記一次Hive平臺清洗數據

場景(簡化)

現有文章表Article和評論表Comment;
一篇文章可以有多個評論;
文章表Article主要字段(articleId);
評論表Comment主要字段(commentId,articleId,content,createTime,lastChangeTime);

問題描述

發現很多文章下出現了評論內容一樣的評論,所以需要對文章的評論進行數據清洗,即同一文章下相同內容的點評只保留修改時間最晚的一條(請忽略是不是同一個用戶評論的問題);

解決步驟

  1. 接到需求當下的第一個想法是遍歷Article表,然後通過UDF調用線上服務,線上服務再拿articleId去處理評論重複的問題,雖然這個方法簡單,但是隻適合小數據量,所以得繼續觀察;
  2. 然後查一下設計清洗的數據量有多少(對於有數據倉庫的請不要在生產庫查詢,防止數據量太大影響線上功能),查詢的結果大概是兩千萬左右,數據量太大,起初的想法不合理,只能換其它的方法;
  3. 詢問了一下同事看有沒有什麼好的解決方案,同事說可以用SQL將需要清洗的數據篩選出來,由於我之前沒有寫過這麼複雜的SQL語句,所以還心存懷疑,但事實證明SQL語句可以,讓我知道了SQL的強大,不能因爲沒寫過就質疑,這一點警醒了我;
  4. 開始寫SQL(Hive平臺支持類SQL語句進行查詢),語句如下:
    SELECT
    	udf_fun ( concat_ws( '&', concat_ws( ',', collect_list ( commentId ) ), concat_ws( ',', collect_list ( lastChangeTime ) ) ) ) 
    FROM
    	(
    SELECT
    	articleId,
    	content,
    	commentId,
    	lastChangeTime
    FROM
    	content 
    WHERE
    	( articleId, content ) IN (
    SELECT
    	articleId,
    	content 
    FROM Comment
    GROUP BY
    	articleId,
    	content 
    HAVING
    	count( * ) > 1 
    	) AS ccc 
    GROUP BY
    	articleId,
    	content
    
  5. 執行Hive任務,在udf_fun中控制好訪問生產環境時間間隔,不要無時間間隔,可能會影響生產環境;

總結

對於4步的SQL其實還可以進行一步完善,但是我嫌麻煩,而且本來就已經產生了幾個臨時表了,再繼續增加臨時表可能會拖慢性能,所以選擇將commentId和最後修改時間連接成字符串發送給UDF,UDF再排一下序篩選一下這個方案,也是挺快的,當然選擇這種方案你得看看你的最長拼接串是多長,如果太長,http請求可能傳輸不了。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章