2017年11月16日 星期四

用 TGOS 全國門牌地址定位服務繪製全家便利商店全國門市地圖

[2022/9/7 現在改推另一個範例: TGOS 批次地址查經緯度 + umap 私房地圖範例: 清冠一號中醫診所地圖] 至於本篇舊文, 可以直接跳到 TGOS 重點提示 那一節查看 TGOS 服務的使用方式。

一、 下載 「全家門市」 地址

這篇我們要列出某大規模連鎖店的全國門市、 用內政部資訊中心所提供的 「批次地址比對服務」 把門牌號碼轉成經緯度、 最後再匯入 umap 私房地圖。 全家門市查詢 有簡單的靜態網頁, 最容易處理, 那就決定用全家當範例了。 用 wget 把所有網頁抓下來, 如 FamilyMart.tgz (包含下面成果的打包壓縮檔)。

for f in familymart*-*.html ; do \
    extract.php -s 'blockquote div div tr td' < $f ; \
done | \
perl -pe 's/<td.*?>/<td>/g; s/\n//g' | \
perl -pe 's#(服務代號.*?<td>)#\n#g' | \
perl -pe 's#</td><td>#,#g; s#^<td>##; s#,$##' | \
grep -v '<img' > summary.csv

想要了解上面這一長串, 建議先把迴圈剝掉, 只拿一個檔案來測試。 它首先用到 extract.php 把各門市的基本資訊 (店名、 電話、 地址) 抓出來。 再來那幾句 perl 先把所有資料擠成一列、 又在每個 「服務代號」 的尾巴重新斷列, 最後把多餘的標籤刪掉。 再用文字編輯器打開 summary.csv , 手動去掉最尾巴的額外字元。

[2023/06/23 重寫、上傳新版的 FamilyMart.tgz ] 接下來:

  1. 資料裡面有一些重複的門市, 把它去掉: sort -n summary.csv | uniq > summary-uniq.csv
  2. 在每一列前面加上一個數字代號欄位,統一採用四位數起跳, 這樣後續要下 join 指令比較方便: perl -pe 'print($.+1000, ",")' summary-uniq.csv > summary-id.csv
  3. 產生 TGOS 所需要的格式 (第一欄數字代號、第二欄地址): cut -d, -f 1,4 summary-id.csv | perl -pe 's/$/,,,/' > tgos-utf8.csv
  4. 編輯 tgos-utf8.csv 手動補上第一列: id,Address,Response_Address,Response_X,Response_Y
  5. autob5 -i utf8 -o big5 > FamilyMart-addr.csv 按照 轉碼 big5 除錯記 從 tgos-utf8.csv 產生 tgos-big5.csv。

二、 TGOS 重點提示

再到 地理資訊圖資雲服務平台 註冊一個帳號。 在 「全國門牌地址定位服務」 功能裡, 每次可以查詢一筆資料。 但我們需要用到 (查詢按鈕下面的) 第三個分頁的 「批次門牌地址比對服務」 功能。 這必須要另外申請才能用。 從 「資料申請」 => 「服務申請」 進去, 在 「關鍵字」 欄填 「地址」, 搜尋到 內政部資訊中心所提供的 「批次地址比對服務」, 給他申請下去。 隔幾天通過後就會收到通知。

使用批次地址比對服務 使用批次地址比對 api key 再回到 「批次地址比對服務」, 照著右邊紫色底的 「要如何取得 API Key」 把申請到的 API Key 剪貼進去。 至於座標系統, 根據 這一篇, OSM 採用 WGS84 (EPSG 4326)。 然後上傳 tgos-big5.csv 試算表。 又把底下的比對參數調到最寬鬆 (像是「允許模糊比對」、「不分單雙號」、忽略村里鄰等等); 「多筆回傳限制」 可以選1, 省得多門牌的店面傳回太多資料反而難處理。 最後按下 「進行批次比對」。

如果失敗, 出現錯誤訊息, 修正後要記得再調整一次下方幾個比對參數, 不然它會變得很嚴格。 我遇過的錯誤包含: 重複的列、 utf8 編碼、 unix 文字檔格式、 欄位錯誤等等。 所以上面有做 uniq、 todos、 autob5、 刪除第一個逗點等等處理。

經過幾十分鐘之後, 就會從 e-mail 收到下載的網址。 假設存檔命名為 ans0.csv。 最前面會多出兩個 bytes, 稱為 BOM。 可以這樣查看: head -n 1 ans0.csv | xxd 如果最前面三個 bytes 是不可顯示的字元: ef bb bf 那就是 BOM 了。 後續如果需要做 join 等等動作時, 可能會製造問題。 可以這樣刪掉: perl -pe 's/^\xEF\xBB\xBF// if $.==1' ans0.csv > ans.csv

有些列顯示「找不到指定的門牌地址」錯誤。 [2023/6/18 不太確定為什麼, TGOS 的 (個別) 門牌地址查詢, 查到的數字不正確。] 如果數量不多, 可以到 google maps, 手動逐一查詢, 查到後在地圖上該處按右鍵, 即可讀出經緯度, 再手動填進 ans.csv。

有了這個 csv, 就可以進一步把 csv 轉 geojson 然後匯入你的 umap 私房地圖了。 [2023/6/29 umap 可以直接吃 csv 檔。 其中必須有一個欄位名稱以 lat 開頭, 另一個欄位名稱以 lon 開頭。] 因為還想做更多後續處理, 這篇就暫時先不展示壯觀的 「全家超商全國門市地圖」 :-)

沒有留言:

張貼留言

因為垃圾留言太多,現在改為審核後才發佈,請耐心等候一兩天。