【解答】sql和其他語言的思考方式

上次的題目( https://www.toutiao.com/i6663783821558678023/ ) 大家都看了嗎,感覺是不是賊簡單,竟然做這種題,簡直侮辱智商,不介意的話我來說下大家心裡是不是這樣解答的。

一、python的解答方式

1.1 數據的存在方式

python等程序語言呢我們會習慣於將數據加載到我們熟悉的數據結構中進行處理,那這裡呢就是一個list ,類似於data=[['00001','00002'],……]。

1.2 數據的處理方式

python這樣的程序語言範式提供給我們的思考方式也就順序、選擇、循環這三種程序結構和各種能簡化操作的數據結構。

面對上面list這樣一個數據結構,我們要完成我們的題目,首先想到的解決方案就是,循環遍歷data,對於每一條數據(例如:['00001','00002'])我們在去data中尋找有沒有與之對應的數據(['00002','00001']),如果有結果就加一。

res = 0 
for d in data:
if [d[1],d[0]] in data:
res += 1
return res/2

二、sql的解答方式

2.1 數據的存在方式

在寫sql語言的時候我們不用關心,數據具體是在哪兒,怎麼存。我們面對的是一個抽象的對象:表,它就代表了數據的存在。

2.2 數據的處理方式

在sql語言中我們面對的就是表這樣的高級抽象,對於數據的變化就無外乎select、filter、join、sum 這樣的幾種操作類型。

那要解決我們的問題我們能首先想到的就是表自身join自身然後再聚合統計。

select count(*)/2 res
from user_friend a
join user_friend b
on a.friend_uid=b.user_id and a.user_uid=b.friend_id

三、spark的解答方式

spark 裡面不管是rdd還是dataframe這兩種api其實和sql中表的抽象是類似的,都有map、filter、join、聚合這幾種範式。所以解決方案和sql的思想類似。

四、終極複雜解決方案

其實 a->b , b->a 這之間只是順序上的差別,a還是那個a,b還是那個b。我們只需要不在乎順序a->b,b->a就是相同的兩條記錄,那我們就只需要統計一下這個表裡面有兩條相同記錄的數據就能知道答案了。

python:

data_tmp = [ d[0]+d[1] if d[0] < d[1] else d[1]+d[0] for d in data]
res = len(data_tmp) - len( set(data_tmp) )
return res

sql(不用join):

select count(1) res
from (
select union_id
from (
select if( friend_uid>user_uid
, concat(friend_uid, user_uid)
, concat(user_uid, friend_uid )
) union_id
from user_friend
)tmp
group by union_id
having count(*)=2
)tmp2

關注眾公號(曾二爺) 和優秀的人一起學習。


分享到:


相關文章: