史上最簡單的推薦系統設計
推薦系統聽上去是高大上的東西,在互聯網多個場景中有廣泛應用
場景1:你在google或百度的廣告后臺,輸入一個關鍵詞提交競價,那么系統就會推薦很多認為你可能需要的關鍵詞。
場景2:你在小游戲網站玩一款小游戲,旁邊會提示你可能喜歡玩的其他小游戲。
場景3:你在電子商務網站下訂單完成購物,底下有一欄推薦你購買的其他產品。
類似場景是不是很熟悉?
現在推薦系統也被定義為大數據的一種典型應用,很多公司給出高薪,不惜代價,要挖能實現推薦系統,機器學習的算法達人。
聽上去很動心是不是,然而,抱歉,我教不了你出去混高薪的那些招,原因很簡單,我也不會。 我的水平很low,沒辦法在算法上和數據挖掘技巧上指導別人,但我有很low的方法,而且在使用中,居然是管用的,如果你已經研究過多款成功的推薦系統,或者自己在以前的學習過程中掌握了非常強大的推薦算法,請忽略此文,以免耽誤您的時間;但換過來,如果您是一個小公司的創業者,一個正在努力提升的基礎程序員,一個公司還沒有搭建推薦系統并且給出了很高的條件找不到合適人才正在發愁的老板,也許這篇文章可以幫到你。
應該是2005年的時候,我對十年前的具體時間記得不是很準確,也許是2006,反正就是那段日子里,百度當時還很弱小,公司內的系統也不復雜,很多東西做的也不是很高大上,嗯,也正是因此,我才有機會去嘗試一些很low但是有用的東西。 當時想試著把商業關鍵詞聚合起來,把關鍵詞的關聯和分類做出來,但是我完全沒經驗,就去請教與我配合的工程師,張懷亭(現在是跟誰學的聯合創始人,CTO)。他說他以前研究生課題就是這個,然后給我看了一篇他寫的論文,然后,我發現,我完全看不懂! 只好死皮賴臉的去請教,雖然算法看不懂,又聽不懂,但不斷追問下好歹明白了幾個最基本的概念,第一,相關推薦的數據基礎是共同推舉數,所謂共同推舉數就是,有多少人共同選擇了A和B,共同推舉越高,顯然相關性越高。第二,如果單純以共同推舉數為推薦的依據,可能會出現一些非常不合理的結果,比如推薦關鍵詞時,相關度未必很高的熱門詞會占主要位置,推薦游戲時也會出現一水的熱門游戲,而不是高度關聯的游戲。所以不能完全依賴于推舉數。基于這些粗淺的理解,我忽略了其他不懂的部分,用簡單粗暴,毫無技術含量的方式做了一套關鍵詞的關聯和推薦模型,跑出來看結果還可以,代碼量,哦,一個下午。
我們以商業關鍵詞的關聯為例來說明,每個廣告主會選擇多個關鍵詞,我認為這是我們的數據源,數據結構只取最簡單的,廣告主id,關鍵詞。 當然,如果我們做電商,可以用消費者購買清單,如果做游戲,可以用玩家玩過的游戲清單,其思路完全一致。
第一步,數據準備
數據源 廣告主的競價記錄數據表,忽略價格等其他因素,只取廣告主id,關鍵詞 兩個字段。
遍歷該數據,整理出兩個新的結構
結構1:關鍵詞熱度表
關鍵詞,總推舉數
結構2:廣告主熱度表
廣告主,總提交詞數
第二步 關聯度計算
遍歷廣告主表,
將該廣告主的所有提交關鍵詞拿出來,做彼此的加權累加。
(這個地方我簡單解釋一下,如果一個廣告主提交了100個關鍵詞,就是100*99的循環,讓每兩個關鍵詞都進行關聯度權值的計算,這個程序員應該都會吧)
(權值的計算,我承認我是拍腦袋的,根據實際,通過對結果的檢查和反思,這里可以改,我們假設目前計算關鍵詞A和關鍵詞B的權值,在每個自循環最內進行權值的累加計算, 權值(A,B)=權值(A,B)+1/(B的共同推舉數開方*當前廣告主提交詞數的開方), 也就是降低熱門詞的權值,以及,一個廣告主如果提交了太多關鍵詞,也降低相關權值。請注意這里還有一個權值(B,A)=權值(B,A)+(1/A的共同推舉數開方*當前廣告主提交詞數的開方),權值(A,B)并不等于權值(B,A),這里需要特別說明一下。)
第三步,結果匯總并優化
數據結構為,關鍵詞1,關鍵詞2,權值。
一對關鍵詞會出現A,B,權值(A,B)和 B,A,權值(B,A),這是有意義的。
下面說幾個問題
第一,遍歷循環會不會太大,比如一個廣告主提交了5萬個關鍵詞,是不是要執行25億次的循環? 對不起,一個廣告主如果提交了太多關鍵詞,我認為這些詞彼此關聯性并不大,如上面公式所示,所以,提交超過1000詞的直接忽略掉,算都不算。這樣計算量就極大降低了。 嗯,偷懶就是這么有借口。
第二,最后結果及中間數組內容會不會太大,會的! 這里我要提及一個特別重要的原則,那就是,實際我們并不需要完全保留每兩個詞之間的相關性,當我去看特定詞的時候,系統給出推薦幾十個已經足夠了,所以,我其實只要保存 每個關鍵詞的top100相關詞就可以,不用所有的結果都存下來。而中間數據,我用了一個簡單粗暴的方法,就是每執行一些記錄,就把當前的所有關鍵詞的top詞表記錄到一個臨時表,然后清空內存重新統計,到最后把這些top相關詞的臨時表按照關鍵詞排序再跑一遍做累加就可以了。
so,其實就是這么簡單。
沒有算法,沒有高逼格的技術,就是最基本的循環,計算,然后寫入數據表。
下面留一下思考題,都是之前我處理過的,當然,都是用比較簡單粗暴的方式處理完的,有興趣的童鞋可以想想
1、以小游戲網站為例
數據結構如下
游戲A,游戲B,相關權值
目前已知有5萬款小游戲,平均每款有50條記錄,也就是數據表有250萬條記錄。
用戶中心,某玩家登陸后,檢索出他歷史玩過的小游戲清單,取最新的20條,基于這20條他玩過的最新小游戲,系統推薦一些其他游戲給他。
SQL 如下
select sum(權值) as 新權值, distinct(游戲B) from 數據表 where 游戲A in (檢索出來的20個歷史游戲列表) group by 游戲B,order by 新權值 desc limit 0,10.
(好幾年沒寫SQL了,也沒測試環境,戰戰兢兢,不知道寫錯沒。)
請問,這樣一條SQL,數據索引應該怎么設計,系統開銷是多少,單臺普通的數據庫服務器大概可以支持每秒鐘多少并發。 如果能正確理解數據索引,這個問題是可以估算出來的。
2,基于今天分享的內容,商業關鍵詞的關聯和推薦做好后,我希望對商業關鍵詞做行業分類,請問下一步應該怎么做?
來自:http://mp.weixin.qq.com/s?__biz=MzI0MjA1Mjg2Ng%3D%3D