6
9

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

写真からランドマークを検出して住所情報を自動取得させてみた

Last updated at Posted at 2019-03-15

概要

いろいろなAPIを利用して、自動で、写真からランドマークを検出し、住所情報も取得した。

利用したAPI

t.jpg

Vision API

vision api.png

https://cloud.google.com/vision/?hl=ja
Googleが提供している画像コンテンツ解析API
写真に写っているランドマークを検出するLANDMARK_DETECTIONや、写っているものを識別してラベルとして返すLABEL_DETECTION、テキスト検出や、顔検出、ロゴサーチ、セーフサーチなどの機能がある。
今回はLANDMARK_DETECTIONを利用して、ランドマークとその緯度経度を検出させる。

事前準備

下記URLに従って、VisionAPIを有効化する必要がある。
https://cloud.google.com/vision/docs/before-you-begin?hl=ja

ローカル環境でPythonなどのライブラリ経由で利用するため、IAMでの認証設定・ライブラリインストールも必要。
https://cloud.google.com/vision/docs/libraries?hl=ja#client-libraries-install-python

Google Maps API

google maps api.jpg

https://cloud.google.com/maps-platform/?hl=ja
Webサイト上にGoogle Mapを載せたり、住所から緯度経度を、緯度経度から住所を取得できたりするAPI。
今回利用したのは、緯度経度から住所情報を取得するGeocoding API
一点注意が必要なのが、レスポンスはすべて英語となっており、日本語での住所情報が欲しい場合は他のAPIを利用する必要がある。

事前準備

同じくGoogle Maps APIを有効化する必要がある。
Google Maps APIは、VisionAPIと違ってAPI Keyが必須なので注意。
参考:Google Maps API を使ってみた

Geo API

geoapi.png

http://geoapi.heartrails.com/
緯度経度から住所情報を取得するAPI。
こちらは日本に特化したものとなっており、日本語で住所情報を取得可能。

試してみた

ターゲット

伏見稲荷大社の写真で試してみる。

fushimi-inari.jpg

住所は〒612-0882 京都府京都市伏見区深草藪之内町68である。

Vision API

今回はpython3

>>> import os, io
>>> from google.cloud import vision
>>> from google.cloud.vision import types
>>> client = vision.ImageAnnotatorClient()
>>> file_name = "Desktop/fushimi-inari.jpg"
>>> with io.open(file_name, 'rb') as image_file:
...     content = image_file.read()
... 
>>> image = types.Image(content=content)
>>> response = client.landmark_detection(image=image)
>>> response.landmark_annotations[0]
mid: "/m/05ldrm"
description: "Fushimi Inari-Taisha"
score: 0.7252039909362793
bounding_poly {
  vertices {
    x: 165
    y: 193
  }
  vertices {
    x: 928
    y: 193
  }
  vertices {
    x: 928
    y: 781
  }
  vertices {
    x: 165
    y: 781
  }
}
locations {
  lat_lng {
    latitude: 34.967139
    longitude: 135.77301
  }
}

見事、descriptionにあるように、ランドマークとしてFushimi Inari-Taishaが検出された。
scoreは確度、bounding_polyは検出された位置を示している。
そして、locationとして緯度経度も取得できた。

Google Maps API

>>> import googlemaps
>>> from pprint import pprint
>>> GOOGLE_MAPS_API_KEY="your API key"
>>> gmaps = googlemaps.Client(key=GOOGLE_MAPS_API_KEY)
>>> latitude = response.landmark_annotations[0].locations[0].lat_lng.latitude
>>> longitude = response.landmark_annotations[0].locations[0].lat_lng.longitude
>>> result = gmaps.reverse_geocode((latitude, longitude))
>>> pprint(result)
[{'address_components': [{'long_name': '68',
                          'short_name': '68',
                          'types': ['premise']},
                         {'long_name': 'Fukakusa Yabunouchichō',
                          'short_name': 'Fukakusa Yabunouchichō',
                          'types': ['political',
                                    'sublocality',
                                    'sublocality_level_2']},
                         {'long_name': 'Fushimi-ku',
                          'short_name': 'Fushimi-ku',
                          'types': ['political',
                                    'sublocality',
                                    'sublocality_level_1']},
                         {'long_name': 'Kyōto-shi',
                          'short_name': 'Kyōto-shi',
                          'types': ['locality', 'political']},
                         {'long_name': 'Kyōto-fu',
                          'short_name': 'Kyōto-fu',
                          'types': ['administrative_area_level_1',
                                    'political']},
                         {'long_name': 'Japan',
                          'short_name': 'JP',
                          'types': ['country', 'political']},
                         {'long_name': '612-0882',
                          'short_name': '612-0882',
                          'types': ['postal_code']}],
  'formatted_address': '68 Fukakusa Yabunouchichō, Fushimi-ku, Kyōto-shi, '
                       'Kyōto-fu 612-0882, Japan',
  'geometry': {'location': {'lat': 34.96718810000001, 'lng': 135.7732651},
               'location_type': 'ROOFTOP',
               'viewport': {'northeast': {'lat': 34.96853708029151,
                                          'lng': 135.7746140802915},
                            'southwest': {'lat': 34.96583911970851,
                                          'lng': 135.7719161197085}}},
  'place_id': 'ChIJ7-v-BhUPAWAR3z0uXSNuPO8',
  'plus_code': {'compound_code': 'XQ8F+V8 Kyoto, Kyoto Prefecture, Japan',
                'global_code': '8Q6QXQ8F+V8'},
  'types': ['street_address']},
 {'address_components': ...以後省略

formatted_addressが住所情報で、構成する要素がaddress_componentsに格納されている。

取得できた住所は、8 Fukakusa Yabunouchichō, Fushimi-ku, Kyōto-shi, Kyōto-fu 612-0882, Japan
英語ではあるが、正しい住所情報を取得できた。

geoAPI

続いて、getAPIで日本語での住所情報も取得する。
APIのエンドポイントはhttp://geoapi.heartrails.com/api/json。ここにGETすればよい
必要なパラメータはこちら

パラメータ
method searchByGeoLocation(固定)
x 経度
y 緯度
>>> url = "http://geoapi.heartrails.com/api/json?method=searchByGeoLocation"
>>> params = {
...         "x": longitude,
...         "y": latitude
...     }
>>> import requests
>>> r = requests.get(url, params=params)
>>> pprint(r.json())
{'response': {'location': [{'city': '京都市伏見区',
                            'city_kana': 'きょうとしふしみく',
                            'distance': 71.82043454757451,
                            'postal': '6120882',
                            'prefecture': '京都府',
                            'town': '深草薮之内町',
                            'town_kana': 'ふかくさやぶのうちちょう',
                            'x': '135.772224',
                            'y': '34.967102'},
                           {'city': '京都市伏見区',
                            'city_kana': 'きょうとしふしみく',
                            'distance': 173.26500637918542,
                            'postal': '6120881',
                            'prefecture': '京都府',
                            'town': '深草稲荷御前町',
                            'town_kana': 'ふかくさいなりおんまえちょう',
                            'x': '135.771117',
                            'y': '34.967266'},
                           {'city': '京都市伏見区',
                            'city_kana': 'きょうとしふしみく',
                            'distance': 238.45040420335357,
                            'postal': '6120888',
                            'prefecture': '京都府',
                            'town': '深草大門町',
                            'town_kana': 'ふかくさだいもんちょう',
                            'x': '135.772471',
                            'y': '34.965043'},
                           {'city': '京都市伏見区',
                            'city_kana': 'きょうとしふしみく',
                            'distance': 247.53084931789914,
                            'postal': '6120807',
                            'prefecture': '京都府',
                            'town': '深草稲荷中之町',
                            'town_kana': 'ふかくさいなりなかのちょう',
                            'x': '135.77084',
                            'y': '34.968474'},
                           {'city': '京都市伏見区',
                            'city_kana': 'きょうとしふしみく',
                            'distance': 282.43664119023936,
                            'postal': '6120806',
                            'prefecture': '京都府',
                            'town': '深草開土町',
                            'town_kana': 'ふかくさかいどちょう',
                            'x': '135.773046',
                            'y': '34.969676'},
                           {'city': '京都市伏見区',
                            'city_kana': 'きょうとしふしみく',
                            'distance': 283.5300564540047,
                            'postal': '6120805',
                            'prefecture': '京都府',
                            'town': '深草開土口町',
                            'town_kana': 'ふかくさかいどぐちちょう',
                            'x': '135.774601',
                            'y': '34.969327'},
                           {'city': '京都市伏見区',
                            'city_kana': 'きょうとしふしみく',
                            'distance': 290.88767776536855,
                            'postal': '6120889',
                            'prefecture': '京都府',
                            'town': '深草直違橋十一丁目',
                            'town_kana': 'ふかくさすじかいばし11ちょうめ',
                            'x': '135.770897',
                            'y': '34.965182'},
                           {'city': '京都市伏見区',
                            'city_kana': 'きょうとしふしみく',
                            'distance': 311.7538119765497,
                            'postal': '6120013',
                            'prefecture': '京都府',
                            'town': '深草祓川町',
                            'town_kana': 'ふかくさはらいがわちょう',
                            'x': '135.769595',
                            'y': '34.967245'},
                           {'city': '京都市伏見区',
                            'city_kana': 'きょうとしふしみく',
                            'distance': 320.4272613869519,
                            'postal': '6120808',
                            'prefecture': '京都府',
                            'town': '深草稲荷榎木橋町',
                            'town_kana': 'ふかくさいなりえのきばしちょう',
                            'x': '135.770798',
                            'y': '34.969375'},
                           {'city': '京都市伏見区',
                            'city_kana': 'きょうとしふしみく',
                            'distance': 330.8874458592692,
                            'postal': '6120811',
                            'prefecture': '京都府',
                            'town': '深草笹山町',
                            'town_kana': 'ふかくさささやまちょう',
                            'x': '135.776632',
                            'y': '34.967298'}]}}

日本語での住所情報として、京都市伏見区深草薮之内町が取得できた。

最後に

個人開発した旅行写真紹介サイト【Where to Visit?】では、このAPI連携を利用して、写真の住所情報やランドマークを自動登録しているので、ぜひ見てみてください。

参照:GAE×DjangoでWebサービスを開発してみた

6
9
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
6
9

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?