PR

HERE Data SDK for Pythonの使い方とチュートリアル解説

Python便利帳
Sponsored

概要

この記事では、HERE Data SDK for Pythonの使い方について、チュートリアルの解説を通じてまとめています。

(この記事は「【HERE WeGo!】ジオファン集まれ!地理空間情報、地図に関する記事を募集しています by HERE Advent Calendar 2022|24日目に登録されています)

【HERE WeGo!】ジオファン集まれ!地理空間情報、地図に関する記事を募集しています by HERE - Qiita Advent Calendar 2022 - Qiita
Calendar page for Qiita Advent Calendar 2022 regarding 【HERE...

HERE Data SDK for Python

機能

「HERE Data SDK for Python」は、HERE platformの機能やコンテンツを、PythonやJupyter Notebookから利用するためのSDK (Software Development Kit)です。

HERE platformを活用することによって、地理空間情報データの解析や可視化を高速に行うことができます。

開発ガイド

HERE Data SDK for Pythonの開発ガイドは

https://jp.developer.here.com/documentation/sdk-python-v2/dev_guide/index.html

に公開されており、英語のAPIリファレンスも用意されています。
この記事でも、こちらのドキュメントに従って解説を行います。

インストール

SDKはhere-platform, here-geotiles, here-geopandas-adapter, here-content, here-inspectorのパッケージにより構成されています。
これらは以下のコマンドにより、pipから一括インストールできます。

pip install --extra-index-url https://repo.platform.here.com/artifactory/api/pypi/analytics-pypi/simple/ here-platform==2.14.0 here-geotiles==2.14.0 here-geopandas-adapter==2.14.0 here-content==2.14.0 here-inspector==2.14.0

資格情報の設定

HERE platformを使用するためには、アカウントを作成して資格情報を取得する必要があります。

こちらの記事

【HERE】Maps API for JavaScriptを試してみた! - Qiita
はじめに この記事は 【HERE WeGo!】ジオファン集まれ!地理空間情報、地図に関する記事を募集しています by H...

を参考にアカウント情報を作成し、HERE Platform Application and Keysの「OAuth 2.0」→「資格情報を作成」→「ダウンロード」からcredentials.propertiesファイルを取得します。
このファイルを

$HOME/.here/credentials.properties (Linux/MacOS)
%USERPROFILE%\.here\credentials.properties (Windows)

に配置して資格情報の設定は完了です。

HERE platformによる地理空間情報の解析と可視化

チュートリアル

HERE Data SDK for Pythonの開発ガイドには複数のチュートリアルJupyter Notebookが公開されています。
このうちのいくつかは、一般公開されていないデータセットを用いているため、適切な許可を取らないと、途中で

AuthenticationException: An error occurred during authentication or authorization with HERE
                    platform: Status 403 -
                    Reason Forbidden
 Response: {"error":"Forbidden","error_description":"These credentials do not authorize access"}

のようなエラーを吐きます。(参考:

HERE maps Python SDK v2 failing to authenticate with the platform
I am struggling with accessing resources on the HERE platfor...

そのため、ここではフリーのデータを用いたInteractiveMapLayersIntro.ipynbを逐行解説しながらSDKの機能を解説していきます。

https://github.com/heremaps/here-data-sdk-examples-python/blob/main/tutorials/InteractiveMapLayersIntro.ipynb

SDKパッケージのインポート

from here.platform import Platform
from here.inspector import inspect, new_inspector
from here.inspector.styles import Color

PlatformはHERE platformとの通信を提供するクラスです。HERE Data SDK for Pythonを利用する際にはほぼ確実にインポートします。
here.inspectorからは、データを可視化するための関数をインポートしています。inspect関数はデータの簡易的な可視化を行い、new_inspector関数により生成されるInspectorクラスは、より詳細な設定を可能にします。
here.inspector.stylesからインポートしたColorは、Inspectorで表示色を設定する際に使用します。

Inspectorの使い方

Inspectorの生成

insp = new_inspector()

new_inspector関数から新規のInspectorを生成できます。

フィーチャーの追加

insp.add_features(json.load(open(countries_path)), name="Countries", style=Color.BLUE)
insp.add_features(json.load(open(volcanoes_path)), name="Volcanoes", style=Color.RED)

add_features関数により、Inspectorにフィーチャー(可視化したいデータ)を登録できます。ここでは、国境データCountriesを青、火山データVolcanoesを赤で表示するように設定しています。

フィーチャーの表示

insp.show()

show関数を用いてInspectorに登録されたデータを可視化できます。

Platformの設定

Platformの生成

platform = Platform()

Platformを初期化します。

カタログの追加

cat = platform.create_catalog(id=f"{ts}", name="name", summary="summary", description="description", billing_tag="ODIN2823")

Platformを通して新たにカタログ(地理空間情報とそれに付随する様々な情報のセット)を作成することができます。
create_catalog関数は、引数の情報を持つ新規のカタログを作成し、Catalogクラスオブジェクトを返します。

カタログ情報の変更

platform.update_catalog(
    hrn=cat.hrn, 
    id=f"c{ts}", 
    name="Countries and volcanoes", 
    summary="A catalog for countries and volcanoes.", 
    description="A catalog for countries and volcanoes.", 
    layers=[countries_layer_details, volcanoes_layer_details]
)

Platformupdate_catalog関数を用いると、作成したカタログの情報を変更することができます。
ここでは国境(countries)と火山(volcanoes)のレイヤーを追加し、それぞれに以下のような情報を設定しています。

countries_layer_details = {
    "id": "countries",
    "name": "countries",
    "summary": "Borders of world countries.",
    "description": "Borders of world countries.",
    "layerType": "interactivemap"
}

カタログのレイヤーにフィーチャーを追加

countries_layer = cat.get_layer("countries")
countries_layer.write_features(from_file=countries_path)

Catalogget_layer関数を用いて、指定したレイヤーに対応したLayerクラスオブジェクトを取得した後、write_features関数を用いてレイヤーにフィーチャーを追加することができます。

カタログのレイヤーの統計情報を表示

countries_layer.statistics

Layer.statisticsから、レイヤーの統計情報を確認できる。例えば以下のように、データのサイズや範囲等の情報がまとめられています。

{'type': 'StatisticsResponse',
 'etag': '"692f28ae8bf171c515de5165d5e22346"',
 'count': {'value': 179, 'estimated': False},
 'byteSize': {'value': 589824, 'estimated': True},
 'dataSize': {'value': 589824, 'estimated': True},
 'bbox': {'value': [-180.0, -85.609038, 180.0, 83.64513], 'estimated': False},
 'properties': {'value': [{'key': 'name',
    'count': 179,
    'datatype': 'string',
    'searchable': True}],
  'estimated': False,
  'searchable': 'ALL'},
 'tags': {'value': [], 'estimated': False},
 'geometryTypes': {'value': ['MultiPolygon', 'Polygon'], 'estimated': False}}

レイヤーの可視化

Platformを通してカタログを作成し、そのレイヤーとしてフィーチャーを追加すると、様々な操作を加えながらデータの一部や全部を抽出することができます。

単一のフィーチャーの取得

feature = countries_layer.get_feature(feature_id="IND")
inspect(feature, name="Selected feature") # 表示

get_feature関数を使うと、feature_idに指定したフィーチャーのみを抽出することができます(ここではインドを指定しています)。抽出したフィーチャーはinspect関数を用いて簡易的に表示できます。

複数のフィーチャーの取得

features = countries_layer.get_features(feature_ids=["IND", "CHN"])
inspect(features, name="Selected features")

get_features関数を使うと、feature_idsに指定した複数のフィーチャーのみを抽出することができます(ここではインドと中国を指定しています)。関数名と引数名がともに複数形になっていることに注意してください。

すべてのフィーチャーに繰り返し操作する

features = list(countries_layer.iter_features())
inspect(features, name="All the features")

iter_features関数によりイテレータが生成され、これを用いて、すべてのフィーチャーにアクセスすることができます。これをリスト化してinspect関数に与えることで、すべてのフィーチャーを表示することができます。

条件に合うフィーチャーを検索する

searched_features = countries_layer.search_features(
    params={"p.name": ["India", "United States of America", "Australia", "Germany"]}
)
inspect(searched_features, name="Searched features")

search_features関数を用いると、条件を満たすフィーチャーを検索できます。検索条件はdictを用いて指定します。ここでは、p.nameがインド・アメリカ・オーストラリア・ドイツのいずれかであるフィーチャーのみを検索して取得しています。

指定した四角領域内のフィーチャーを取得する

insp = new_inspector()

bbox = (68.1766451354, 7.96553477623, 97.4025614766, 35.4940095078)
bbox_features = countries_layer.get_features_in_bounding_box(bbox)
insp.add_features(bbox_features, name="Features in bounding box")

box_polygon = shapely.geometry.box(*bbox)
insp.add_features(box_polygon, name="Search box", style=Color.GRAY)

insp.show()

get_features_in_bounding_box関数を使うと、指定した四角領域(bounding box)内に存在するフィーチャーのみを抽出します。領域の表現にはtupleが用いられ、それぞれの要素が(最小経度, 最小緯度, 最大経度, 最大緯度)を指定します。今回は

  • 緯度: 約68.18 ~ 97.40度
  • 経度: 約7.97 ~ 35.49度

を指定し、その中に含まれている・国境が(ギリギリ)掛かっている国を抽出しています。
また、四角領域自体も描画するため、今回は簡易的なinspect関数ではなく、new_inspector関数によりInspectorを作成して可視化を行っています。

指定した半径内のフィーチャーを取得する

insp = new_inspector()

radius_search = countries_layer.spatial_search(lat=0, lng=30, radius=1000000)
insp.add_features(radius_search, name="Features within radius")

circle = Point(30, 0).buffer(10)
insp.add_features(circle, name="Search radius", style=Color.GRAY)

insp.show()

spatial_search関数を用いると、指定した中心点から一定距離半径内にあるフィーチャーのみを抽出することができます。引数にはlat(緯度)、lng(経度)、radius(半径:メートル)を指定します。

ここでも円形領域を描画していますが、shapely.geometryPoint (.buffer)では、メートルではなく緯度経度で指定する必要があります。中心点はPoint(30, 0)で指定できる一方、半径はbuffer(10)で表現しています。これは、赤道上の緯度1度が約111kmであることを利用して

$$1{,}000{,}000\,\mathrm{m}=1{,}000\,\mathrm{km}$$

$$\frac{1{,}000\,\mathrm{km}}{111\,\mathrm{km/{}^\circ}}\fallingdotseq 10^\circ$$

と近似することができるためです。

指定した(任意)領域内のフィーチャーを取得する

feature = countries_layer.get_feature(feature_id="USA")
geometry = feature["geometry"]
geometry_search = volcanoes_layer.spatial_search_geometry(geometry=geometry)
inspect(geometry_search, name="Volcanoes in USA", style=Color.RED)

spatial_search_geometry関数を用いると、四角形や円形でない任意の領域の内部にあるフィーチャーのみを抽出することができます。また、オプションとして半径radiusを指定することもできます。
ここではget_feature関数を用いて国境のレイヤーからアメリカの領域を抽出し、その領域内に含まれる火山のフィーチャーを取得しています。

チュートリアルの次は?

冒頭で紹介した開発ガイド

https://jp.developer.here.com/documentation/sdk-python-v2/dev_guide/index.html

には他にも、ロケーションサービスへのアクセスやPandas・GeoPandasライブラリとの連携、機械学習プラグインの利用法なども紹介されていますので、APIリファレンス

https://jp.developer.here.com/documentation/sdk-python-v2/api_reference/index.html

と合わせて参照してください。

もっと知りたいこと、感想を教えてください!