鄧曉斌
(1.江西水利職業學院,江西 南昌 330013)
隨著互聯網和移動通信的高速發展,人們可以輕松訪問網絡上的大量數據,其中興趣點(POI)數據尤其受到大家的喜愛,如在滴滴打車上可實時查詢附近的滴滴車輛POI信息,百度地圖上可查詢周邊的美食店POI信息等。POI數據是由真實地理實體抽象成的點,其分布與城市的經濟活躍度呈正相關,大多數分布在經濟活躍度較高的區域[1]。由于其獲取成本低、屬性信息量大等特點,POI數據被很多行業所采用,如曹芳潔[2]等利用POI數據研究了城市的空間結構;趙智勇[3]利用POI數據對城市的功能區位進行了劃分;徐智邦[4]等則利用POI數據對城市道路進行了自動化提取。由此可見,POI數據具有重要的實際價值,因此如何獲取POI數據成為一個重要問題。
Python是一種面向對象、解釋型的計算機程序設計語言,是一種功能強大的通用型語言[5],已被廣泛應用于圖形處理、網絡編程、網絡爬蟲、數據分析挖掘、機器學習等領域。鑒于Python在網絡爬蟲和數據分析方面的強大功能,本文采用Python對互聯網POI數據進行爬取和挖掘。
對于POI的概念,國內外學者給出了不同的論述,李霖[6]等認為POI作為一種代表真實地理實體的點狀地理空間大數據,是地理空間中具有標志意義的地理對象;Maceachren A M[7]等則認為POI數據集合不僅具有傳統大數據5V(數據量大、處理速度快、多樣性、準確性、蘊含價值)特點,而且單體POI數據包含了實體的名稱、經緯度、地址、類型、電話、行政區等信息[8];綜合國內外的表述,本文認為,POI是點狀數據,具有豐富的屬性信息,廣泛地分布在互聯網中,是人們日常生活中非常感興趣的一種空間 位置。
POI以多種形式存在,最常見的是電子地圖上與社會經濟密切相關的地理實體點要素,如圖1所示,通過百度地圖檢索出某地區的旅游景點POI信息。在某些情形下,POI也泛指一切受關注程度高于普通點要素的地理點[8]。互聯網上很多論壇、博客、社交軟件等可進行用戶簽到,形成了多種多樣的POI數據。另外,人們日常生活中形成的活動軌跡也是一種POI數據,如乘車GPS軌跡、手機位置定位等。

圖1 旅游景點 POI實例
POI主要通過電子地圖平臺(百度地圖、高德地圖、騰訊地圖等)獲取,其數據信息量大且精度較高、更新及時。這些電子地圖的網站可通過檢索接口或網頁爬取技術獲得POI。還有一些非電子地圖的網站存在很多POI數據,如微博、大眾點評網、美團網等,同樣可通過網頁爬取技術獲得POI。
本文的主要目的是通過對互聯網中的POI數據進行爬取,獲得有價值的POI信息,從而為POI增值業務提供數據基礎。由于電子地圖是POI數據來源的重要途經,且百度地圖在人們日常生活中的使用頻率較高,因此本文選擇爬取百度地圖POI數據。
硬件設備主要為電子計算機,軟件設備主要包括Python2.7、Excel、txt記事本以及百度地圖開放平臺。本文以百度地圖為平臺,構建百度地圖POI數據爬取框架,如圖2所示,以Excel和txt記事本數據格式輸出成果。

圖2 基于百度地圖的POI數據爬取框架
由于POI數據類型眾多,不可能爬取互聯網上所有類型的POI數據,因此本文以爬取南昌餐館POI數據為例,根據模型框架,詳細介紹了POI數據爬取的過程。
使用百度地圖開放的各種功能和數據前,必須先成為百度的用戶,可下載百度App進行掃碼注冊,也可采用QQ或微信等形式注冊登入。
進入百度地圖開放平臺,登錄“控制臺”,在“應用管理”中創建應用。百度對于每個用戶的AK密鑰配額是有限度的,大多數未認證過的用戶每天不能超過10萬次,每min不能超過6 000次。
由于使用一次AK密鑰生成的URL最多能顯示 20個POI數據,同時在特定的坐標范圍內,一次只能生成20個URL,因此采用AK生成的URL頁面最多可爬取400個POI數據。如果POI數據量超過400,則需對區域進行裁剪分割,使每個子區域的POI數據量不超過400個,再分別對每個子區域進行頁面爬取。
3.3.1 小數據量
在爬取POI數據量≤400的情況下,可直接在URL地址欄里輸入以下信息:http://api.map.baidu.com/place/v2/search?query=餐館®ion=南昌&page_size=20&page_num=0&output=json&ak=3kHNz4jtBc2t Ar8RMAQZAyBgEa4vWtsa,其中query代表查詢“餐館”,region代表查詢的區域為“南昌”, page_size代表每個頁面顯示20個POI數據,page_num代表查詢的頁面,output代表輸出的數據格式為JSON,ak為密鑰。將page_num依次設置為1、2、…、19,可得到不同頁面的POI數據。該類POI數據包含餐館名稱、餐館位置(經緯度)、地址、省份、城市、轄區、街道號、電話等大量重要信息。南昌餐館POI數據的JSON樣式為:


當把page_num設置為20時發現,JSON文件內容變成以下情況,里面沒有POI數據,說明用一次AK只能顯示20個頁面。

JSON數據格式類似于Python中的數字字典形式,因此利用Python語言能非常方便地將其轉換為CSV或Excel文件。利用Python語言將POI的JSON數據格式轉換為CSV格式的代碼為:

南昌餐館POI數據的CSV格式如圖3所示。

圖3 POI數據的CSV格式
3.3.2 大數據量
針對POI數據量超過400的情況,需將該范圍劃分為多個小區域,使每個小區域內的POI數據量不超過400。若需要尋找百度地圖中南昌市范圍內所有的餐館POI數據,則首先需將南昌市的地理位置范圍確定下來,可通過百度的坐標拾取功能來獲得。南昌市地圖的左下角的緯度為28.163 652、經度為115.447 208,右上角的緯度為29.127 212、經度為116.572 405。
從上述URL地址信息中可知bounds(相當于 region)和page_num兩個重要變量,其中bounds={左下角緯度,左下角經度,右上角緯度,右上角經度},代入南昌市的范圍數據bounds={28.163 652, 115.447 208,29.127 212,116.572 405},整個南昌市包含的餐館POI超過400個,因此需對該范圍進行切割。如圖4所示,對bounds范圍進行矩形分割,得到4個小矩形,若小矩形范圍仍過大,則需進一步切割,以此類推,直到每個小矩形內的POI數據量不超過400。page_num的取值范圍為0~19。一個矩形坐標范圍內包含20個page_num,做一次切割就有4×20=80個page_num,每個page_num里存放20個POI,則一次切割后一共能爬取80×20=1 600個POI;若將4個小矩形再做切割,產生更小的矩形,則兩次切割后一共能爬取1 600×4=6 400個POI。

圖4 地圖范圍切割
爬取整個頁面的POI數據,需要執行多個循環,Bounds=[rectangle1,rectangle2,rectangle3,rectangle4],Page_nums=[0,1,2,…,19]。其偽代碼為:

根據上述原理,可把POI的爬取過程分為3個階段:①生成bounds列表;②生成URL列表;③將爬取的POI數據保存到txt文件。其中,生成bounds列表的完整代碼為:

’這段代碼生成的是矩形分割后的多個矩形范圍坐標具體運行結果為:

生成bounds列表后,再對page_num從0~20進行遍歷,即可得到URL列表,具體代碼為:

運行結果中的一個例子為:

將爬取的POI數據保存到txt文件,具體代碼為:


代碼執行后生成的南昌餐館POI的txt文件格式如圖5所示。

圖5 南昌餐館POI數據的txt文件格式
POI數據不僅具有空間位置信息,而且具有豐富的屬性信息,能為眾多行業提供數據支撐。本文詳細介紹了百度地圖中南昌餐館POI數據的爬取過程,采用功能強大的Python語言進行開發,取得了良好效果,下一步將對爬取的數據進行深入分析,從而挖掘出有用的商業價值。