從0構建AI推薦系統demo(資料準備)
前言
推薦系統一直以來都是人工智慧領域中較為火熱的研究方向之一,最近公司需要構建常見的資訊類推薦系統,本人也從無到有、從0開始構建AI推薦系統demo版。此篇主要講述最基本的資料準備中,最最最最基本的常用操作。
一、資料準備
記得之前看到過一句話,大致意思是說:資料和特徵決定了機器學習的上限,而模型和演算法只是不斷逼近這個上限而已。
這話說的特別有道理,優質的資料來源可以極大的提高AI訓練的效率。目前來說,資料的主要來源如下:
資料主要來源:
- 網路爬蟲獲取;
- 開源資料集提供;
- 購買優質的資料來源;
- 等等等等
資料的主要種類:
- 1. 交易資料。
- 主要包括電子商務資料、網際網路點選資料、銷售系統資料、CRM)系統資料、公司的生產資料、庫存資料、訂單資料、供應鏈資料等。
- 2. 行動通訊資料。
- 移動裝置上的軟體能夠追蹤和溝通無數事件,從運用軟體儲存的交易資料(如搜尋產品的記錄事件)到個人資訊資料或狀態報告事件(如地點變更即報告一個新的地理編碼)等。
- 3.人為資料。
- 主要包括電子郵件、文件、圖片、音訊、視訊,以及通過微信、部落格、推特、維基、臉書、Linkedin等社交媒體產生的資料流。這些資料大多數為非結構性資料,需要用文字分析功能進行分析。
- 4.機器和感測器資料。
- 主要包括來自感應器、量表和其他設施的資料、定位/GPS系統資料等。例如智慧溫度控制器、智慧電錶、工廠機器和連線網際網路的家用電器的資料。來自物聯網的資料可以用於構建分析模型,連續監測預測性行為(如當感測器值表示有問題時進行識別)等。
本文使用的資料主要為:
1. 前期採用網路爬蟲獲取資料;
2. 中期尋找網上開源資料集中的資料參與訓練;
3. 後期...後期再說...
二、基本資料獲取
針對目標資料來源不同,獲取的方式也會有所差異。本系列文章主要獲取金融財經中資訊類的新聞資料,用以構造最基本的資料層。
0. 網上開源資料集
這是非常快速有效獲取資料的方法之一,一般資料量都很大,並且欄位豐富,內容質量也可以,但是侷限多多,別的不說,由於這些好的資料來源來自國外,下載速度異常的慢,並且N次因為網路錯誤導致下載失敗,還好本人有耐心。。。哎,說多了都是淚,堅持下載到最後,得到約31萬條資料,解壓前570M,解壓後一個多G,都是新聞類的資訊,抽樣來看,大部分是前年和去年的,每條資訊以json檔案的格式儲存,如下所示:
{
"organizations": [],
"uuid": "245bd81f0ae706b4f18a43ede70ed85b80c581a8",
"thread": {
"social": {
"gplus": {
"shares": 0
},
"pinterest": {
"shares": 0
},
"vk": {
"shares": 0
},
"linkedin": {
"shares": 0
},
"facebook": {
"likes": 0,
"shares": 0,
"comments": 0
},
"stumbledupon": {
"shares": 0
}
},
"site_full": "news.eastday.com",
"main_image": "",
"site_section": "",
"section_title": "",
"url": "http://news.eastday.com/eastday/13news/auto/news/world/20161002/u7ai6083740.html",
"country": "CN",
"domain_rank": 363,
"title": "韓國宣佈“薩德”最終部署地引發新一輪抗議",
"performance_score": 0,
"site": "eastday.com",
"participants_count": 0,
"title_full": "韓國宣佈“薩德”最終部署地引發新一輪抗議",
"spam_score": 0.077,
"site_type": "news",
"published": "2016-10-02T08:00:00.000+03:00",
"replies_count": 0,
"uuid": "245bd81f0ae706b4f18a43ede70ed85b80c581a8"
},
"author": "",
"url": "http://news.eastday.com/eastday/13news/auto/news/world/20161002/u7ai6083740.html",
"ord_in_thread": 0,
"title": "韓國宣佈“薩德”最終部署地引發新一輪抗議",
"locations": [],
"entities": {
"persons": [],
"locations": [],
"organizations": []
},
"highlightText": "",
"language": "chinese",
"persons": [],
"text": "\n2016年10月2日 15:25 \n\n韓國民間團體30日在國防部門前舉行抗議“薩德”示威活動。攝影:人民網記者馬菲 \n人民網韓國10月2日電 韓國國防部30日宣佈,將“薩德”反導系統(末段高空區域防禦系統)的“最終”部署地確定為慶尚北道星州郡的星州高爾夫球場。 \n自韓國政府7月13日宣佈將“薩德”部署在慶尚北道星州郡星山炮臺以來,星州居民強烈抗議的呼聲便從未間斷。迫於壓力,韓國國防部於8月下旬選出星州郡內另外3處部署候選地進行考察,分別為星州高爾夫球場、厭俗山和喜鵲山。 \n韓國國防部長官韓民求30日當天向國會各黨派說明情況,並提交了有關評估報告。報告稱,與其他兩個候選地相比,星州高爾夫球場具備必要的基礎設施,能夠保證“薩德”反導系統在2017年底完成部署。 \n而就在兩個多月前,韓國國防部宣佈星山炮臺為“薩德”部署地時,也堅稱這裡是最佳部署地點。有輿論批評認為,政府在重要的國家安全決策上朝令夕改,加重了混亂局面,並損害了政府的透明性和信任度。 \n星州高爾夫球場位於星州郡政府辦公樓以北18公里處,海拔680米,高於海拔383米的星山炮臺。韓國國防部表示,星州高爾夫球場附近民宅較少,有助於平息民眾對“薩德”雷達輻射危害的質疑,且面積也比星山炮臺大,更便於架設雷達和攔截系統。 \n據稱,韓國國防部下一步將與擁有星州高爾夫球場產權的韓國樂天集團開展購地談判。韓媒指出,星州高爾夫球場的購置費用將超過1000億韓元(1美元約合1101韓元),且須由韓國政府全部承擔。韓國政府能否與樂天集團達成協議,以及能否經過國會批准獲得購地預算仍存在諸多變數,因此部署“薩德”仍將面臨挑戰。 \n儘管韓國政府更換“薩德”部署地是為了消除民眾的不滿情緒,然而韓國國內抗議“薩德”的聲浪卻並未因此平息。在星州高爾夫球場部署“薩德”後,雷達將會朝向金泉市方向,金泉市居民對此表示出強烈抗議。在未正式宣佈“薩德”新的部署地之前,金泉市民眾已舉行了1萬餘人蔘加的反對部署“薩德”動員大會,並多次舉行燭光集會表達抗議。 \n金泉市人口超過14萬,大約是星州郡的3倍。韓媒稱,一旦部署地選在星州高爾夫球場,金泉市居民將進行全面抗議,當地居民對於部署“薩德”的強烈反對態度將使韓國政府面臨更大壓力。30日當天,國防部官員前往金泉市就更改“薩德”部署地的決定進行說明,但當地官員拒絕了會面。 \n自韓國宣佈部署“薩德”反導系統以來,民眾多次在國防部門前進行抗議活動。30日中午,本報記者在國防部門前看到,眾多警察在該處嚴加把守,並開始在門前設定多層鐵絲網以防止抗議人群靠近。下午1點半左右,由韓國多個市民團體共同成立的“反對部署‘薩德’全國聯盟”在國防部門前舉行反對“薩德”抗議活動,人們手舉反對“薩德”的標語,高呼口號要求政府撤回部署決定。 \n“韓國不存在‘薩德’的最佳部署地,撤回部署決定才是唯一有效的辦法。”該聯盟在國防部門前宣讀宣告稱,國防部現在推翻了自己之前的說法,又表示星州高爾夫球場更適合部署“薩德”,這完全沒有任何說服力,說明其在確定部署地時根本沒有明確的考察標準。韓國政府無視民眾的生存安全,無視與周邊國家關係的惡化,強行推進部署薩德,破壞地區和平,這絕對不能容忍,一定要阻止在韓國部署“薩德”。 \n“部署‘薩德’到底是為了保護誰的安全?”韓國女大學生鄭有齡在抗議活動中激憤地表示,不管是星州還是金泉,韓國的任何一個地方都不適合部署薩德。韓國已有許多專家論證過在韓國部署“薩德”並不能保衛韓國安全,然而國防部卻完全無視這些聲音,一意孤行堅持要部署“薩德”,這到底是為了保護韓國國民的國防部,還是為了保護美國的國防部? \n當天下午,韓國五大宗教之一的圓佛教也在國防部門前舉行了反對“薩德”的抗議活動。 \n在韓國國防部的對面坐落著韓國戰爭紀念館,二者相對而立。在戰爭紀念館的廣場上,孩子們的嬉笑聲夾雜著遠處的抗議聲,聽起來令人唏噓。戰爭紀念館裡,民眾回顧那段悲痛的歷史,期盼和平,祈禱戰爭不再重演;國防部裡,部署“薩德”、確定“薩德”部署地等決定卻接連傳出,不斷加劇緊張局勢。兩個地方只有一路之隔。 \n\n\n韓國民間團體30日在國防部門前舉行抗議“薩德”示威活動。攝影:人民網記者馬菲 \n上一頁 下一頁 \n\n韓國民間團體30日在國防部門前舉行抗議“薩德”示威活動。攝影:人民網記者馬菲 \n上一頁 下一頁 \n\n韓國國防部正門。攝影:人民網記者馬菲 \n上一頁 下一頁 \n\n警察在國防部門前把守以防抗議人群靠近。攝影:人民網記者馬菲 \n上一頁 下一頁 \n\n抗議人群將反對薩德的標語貼在國防部門前的鐵絲網上。攝影:人民網記者馬菲 \n上一頁 下一頁 \n\n韓國民間團體30日在國防部門前舉行抗議“薩德”示威活動。攝影:人民網記者馬菲 \n上一頁 下一頁 \n\n位於韓國國防部對面的韓國戰爭紀念館。攝影:人民網記者馬菲 \n上一頁 下一頁 \n\n韓國小朋友在戰爭紀念館廣場上嬉戲。攝影:人民網記者馬菲 \n",
"external_links": [],
"published": "2016-10-02T08:00:00.000+03:00",
"crawled": "2016-10-02T11:45:54.531+03:00",
"highlightTitle": ""
}
由於資料量過大,所以每個資訊的內容多種多樣,在設計資料清洗時經常會發生意想不到的情況,本人目前只簡單的處理一部分,畢竟重點是先搭建出來一個推薦系統的demo,至於資料量,在演算法層面上會進行進一步處理,等有時間了,再進行深層次的挖掘。
1. 通過JavaScript在前端獲取(僅供參考)
講真,要不是有特殊的資料來源,本人都不知道JavaScript在前端下載資料這麼6...,爬蟲使用久了之後,體驗很深的一點在於網站的請求很費解,費時費力,JavaScript方式雖然簡單,但是侷限性特別大。獻上程式碼如下:
function downloadData(data){
var fso = new ActiveXObject("Scripting.FileSystemObject");
var f=fso.createtextfile("D:\a.txt",2,true);
f.write(data);
f.close();
}
如程式碼所示,JavaScript中採用的是新建ActiveXObject物件進行檔案操作,蛋疼的是,ActiveXObject物件目前只對IE瀏覽器有效!!!親測在chrome瀏覽器、Microsoft Edge瀏覽器均無法使用,網傳Firefox瀏覽器同樣無法使用。
newObj = new ActiveXObject(servername.typename[, location])
JavaScript中ActiveXObject物件是啟用並返回 Automation 物件的引用。
ActiveXObject 物件語法有這些部分:
其中newObj是必選項。要賦值為 ActiveXObject 的變數名。
servername是必選項。提供該物件的應用程式的名稱。
typename是必選項。要建立的物件的型別或類。
location是可選項。建立該物件的網路伺服器的名稱。
Automation伺服器至少提供一類物件,例如字處理應用程式可能提供應用程式物件、文件物件和工具欄物件。
使用JScript讀寫本地檔案時,會使用Scripting.FileSystemObject控制元件,建立ActiveXObject物件。
注:ActiveX簡介
ActiveX 控制元件廣泛用於 Internet。它們可以通過提供視訊、動畫內容等來增加瀏覽的樂趣。不過,這些程式可能出問題或者向您提供不需要的內容。在某些情況下,這些程式可被用來以您不允許的方式從計算機收集資訊、破壞您的計算機上的資料、在未經您同意的情況下在您的計算機上安裝軟體或者允許他人遠端控制您的計算機。一般軟體需要使用者單獨下載然後執行安裝,而ActiveX外掛是當用戶瀏覽到特定的網頁時,IE瀏覽器即可自動下載並提示使用者安裝。 ActiveX外掛安裝的一個前提是必須經過使用者的同意及確認。考慮到這些風險,您應該在完全信任發行商的情況下才安裝這些程式。
異常處理:
異常名:
“Automation 伺服器不能建立物件”的異常
原因:
使用JScript讀寫本地檔案時,會使用Scripting.FileSystemObject控制元件。
但是IE預設是不允許執行這類“未標記為安全執行指令碼的ActiveX控制元件”的。
因此執行下行程式碼時:
fso = new ActiveXObject("Scripting.FileSystemObject");
會丟擲異常。
異常解決方法:
在IE瀏覽器中並不是預設開啟相應的ActiveX的相關控制元件的,需要手動開啟,方法如下:
1. 在IE瀏覽器中開啟Internet選項卡:
2. 安全欄中找到自定義級別,開啟後找到ActiveX空間相關的內容,如下:
將預設禁用的相關操作開啟即可。
注意:
- 開啟禁用的ActiveX控制元件具有一定的風險性,為了防止惡意指令碼通過修改後的IE瀏覽器修改、操控本地檔案,建議啟用此選項除錯程式碼、下載資料後,恢復預設選擇!!!
2. 通過爬蟲獲取(主要推薦)
通過爬蟲獲取資料,此內容較多,將通過另外單獨的文章分析。
3. 最最基礎程式碼分析
'''
從介面中獲取除了主要內容之外的資料,寫入MySQL
'''
import pymysql
def write2mysql(list):
conn = pymysql.connect(host="localhost", user='root', password='123456789', database = 'news', charset='utf8')
cursor = conn.cursor();
sql = "INSERT INTO docList(news_id, title, time, source, abstract) values " \
"('%s','%s','%s','%s','%s')" % (list[0], list[1], list[2], list[3], list[4])
try:
cursor.execute(sql)
conn.commit()
except:
conn.rollback()
# 要求檔案為utf-8型別
def cleanData(dataFilePath):
with open(dataFilePath, "r",encoding="utf-8-sig") as f:
allData = f.read()
cleandData = allData.replace("||", "|")
dataList = cleandData.split("|,")
for oneData in dataList:
try:
oneDataList = oneData.split("|")
resultDataList = [oneDataList[0], oneDataList[1], oneDataList[2], oneDataList[3], oneDataList[5]]
write2mysql(resultDataList)
except:
continue
if __name__ == '__main__':
dataFilePath = "D:/data.txt"
cleanData(dataFilePath)
注意點:日期、去除 \ufeff、MySQL去重、Python字串格式
- 日期
由於獲取的日期為字串格式:“2018-08-23 21:21”,直接採用字串儲存,沒有轉換成時間戳等形式。但,可能後期存在問題。
- 去除 \ufeff
去除 \ufeff,最直接的辦法是開啟檔案時,將編碼格式有 encoding= “utf-8” 改為 encoding="utf-8-sig"。
- Python字串格式
字串格式匹配,%s、%d、%f 等的使用,省去構造MySQL語句的書寫模式。
- MySQL去重
去除重複的相同資料,儲存唯一ID最小的資料。
1. 找出所有重複記錄的ID
SELECT
(唯一ID)
FROM
TABLE_NAME
WHERE
-- 根據篩選欄位選出重複的資料
(篩選欄位) IN (
SELECT
(篩選欄位)
FROM
TABLE_NAME
GROUP BY
(篩選欄位)
HAVING
count(篩選欄位) > 1
)
AND
(唯一ID) NOT IN (
SELECT
min(唯一ID)
FROM
TABLE_NAME
GROUP BY
(篩選欄位)
HAVING
count(篩選欄位) > 1
)
2. 刪除1中重複的資料
DELETE FROM TABLE_NAME WHERE (唯一ID) IN (.., .., 1中的ID結果 .., ..)