ユゲタです。
「GPS」とかけまして、
「流行のウィルス」とときます。
そのココロは・・・
エイセイ(衛生と衛星)管理が重要です。
GPS検索は、リアル連携サービスの基本作法
なんちゃらGO!系のゲームアプリを始めとして、スマートフォンで誰もがGPSの恩恵を受けて、おもろいゲームや、便利なサービスを受けられる時代になりました。
いまさらGPSがなんじゃろ?という人は、今回の記事はお控えください。
全国の薬局の一覧データを厚労省のサイトから取得できることが分かったのですが、
その一覧データには、郵便番号と住所と電話番号しか情報が無かったため、GPS値を付ける処理をつなげて、かなり利用頻度の高いいい感じのリストデータを作ることに成功しました。
そして、それを自分のスマートフォンで見た時に、近くの薬局を検索するモードを付ける機能を作っているんですが、
利便性を考えて、jsonデータで保存しているデータを、jqコマンドで、一定距離以内のデータのみ取得して、ついでにそれを距離数でソートして、近い順リストを作ろうと考えました。
思いの外、簡単にできたので、そのソースコードを惜しまず掲載したいと思います。
※一覧リストデータは、お手持ちのGPSデータをお使いください。
データとソース
{"lat":35.168599,"lon":136.938189,"address":"〒464-0850名古屋市千種区今池5-2-3共栄ビル1階","medicalId":"010,058,1や千種58","pref":"aichi"}
{"lat":35.166803,"lon":136.946011,"address":"〒464-0848名古屋市千種区春岡1-5-6池下ヤママンビル1階","medicalId":"010,084,7や千種84","pref":"aichi"}
{"lat":35.166370,"lon":136.962207,"address":"〒464-0037名古屋市千種区楠元町2-33","medicalId":"010,110,0や千種110","pref":"aichi"}
{"lat":39.708790,"lon":140.119910,"address":"〒010-0011秋田市南通亀の町14-20","medicalId":"01・4015・9","pref":"akita"}
{"lat":40.819890,"lon":140.747278,"address":"〒030-0822青森市中央二丁目13-14","medicalId":"01-4029-3青薬29","pref":"aomori"}
{"lat":35.581225,"lon":140.127128,"address":"〒260-0834千葉市中央区今井1-20-9","medicalId":"01-0086-7","pref":"chiba"}
{"lat":33.836017,"lon":132.769322,"address":"〒790-0012松山市湊町三丁目7の5番地","medicalId":"01-4018-4","pref":"ehime"}
{"lat":36.061672,"lon":136.220448,"address":"〒910-0006福井市中央1-9-30","medicalId":"01-40055","pref":"fukui"}
{"lat":33.602265,"lon":130.414716,"address":"〒812-0044福岡県福岡市博多区千代1丁目17-1","medicalId":"034,001,2","pref":"fukuoka"}
{"lat":37.830996,"lon":140.453785,"address":"〒960-0201福島市飯坂町十綱町7","medicalId":"0140272","pref":"fukushima"}
{"lat":35.445873,"lon":136.774539,"address":"〒502-0817岐阜市長良福光2667","medicalId":"01,0004,7岐薬4","pref":"gifu"}
{"lat":36.391233,"lon":139.075371,"address":"〒371-0016前橋市城東町4-3-1","medicalId":"01,0011,5前薬11","pref":"gunma"}
{"lat":34.392842,"lon":132.459442,"address":"〒730-0035広島市中区本通8-29","medicalId":"01,4056,8","pref":"hiroshima"}
上記のように、latとlonというkeyに緯度(lat)経度(lon)情報をそれぞれ格納してあります。
※全国データが膨大なので、一部抜粋にしています。
これを、jqで以下のようにすることで、半径100キロメートル以内のデータのみを取得することができます。
$ jq --slurp --raw-output '[.[] | {distance : ( (((.lat | tonumber - %現在地の緯度 | pow(.;2) | tonumber) + (.lon | tonumber - %現在地の経度 | pow(.;2) | tonumber))) | sqrt *100) | select(. <= 100) , address:.address} ] | sort_by(.distance)' lists.json
解説
jqコマンドの中身を順を追って解説します。
まず、latとlonの値から、現在値の緯度経度をそれぞれ差分を求めます。
次に、それをそれぞれ2乗して、足します。
※2乗は、pow(.;2)です。
その値を平方根処理(sqrt)して100を掛けることで、距離が出力されます。
さらに、その計算後の値をselectで100(km)以下の条件をつけて、sort_byでdistanceにセットすると、完了です。
ちなみに、このデータは、厳密な100kmでの判定ではなく、GPS値の1°を大体100kmとして計算するようにしています。
注意点としては、100mぐらいの誤差が出てしまいますが、もっと厳密にしたい方は、内部の計算式を厳密パターンを作ってみてください。
全国で5万件オーバーぐらいの調剤薬局のリストですが、jqコマンドが意外と早い事にビックリすることでしょう。
0 件のコメント:
コメントを投稿