Excel の WEBSERVICE 関数で SPARQL その2

前回の記事 [Excel の WEBSERVICE 関数で SPARQL その1](http://qiita.com/frogcat/items/27a558300c65afdc0189) では、Excel の WEBSERVICE 関数を使って SPARQL を実行し、必要なデータを取得する方法を紹介しました。この記事では [GeoNames.jp](http://geonames.jp/) の URI とリンクセットを使って DBpedia Japanese からデータを取得する方法を紹介します。

# 1. シナリオ

東京23区の公式ホームページのリストを作ります。

![image](https://qiita-image-store.s3.amazonaws.com/0/82494/29729f72-2e96-f7ec-cfcd-9d1a7d0065f9.png)




# 2. 手順

**B2** セルに以下の関数をコピーします


```B2.
= FILTERXML(WEBSERVICE("http://ja.dbpedia.org/sparql?query=" & ENCODEURL("select ?x where {?s <http://www.w3.org/2002/07/owl#sameAs> <http://geonames.jp/resource/東京都" & A2& "> ; <http://ja.dbpedia.org/property/外部リンク> ?x . } ")),"//binding/*")
```

以下のように値が取得できていたらまずは成功です

![image](https://qiita-image-store.s3.amazonaws.com/0/82494/ac87820f-7b82-9927-52cf-757b8dbcdac7.png)

**B2** を **B3** 以下にコピーすれば完了です 

![image](https://qiita-image-store.s3.amazonaws.com/0/82494/fe449c91-696f-60ac-58f4-228e47ac566a.png)

クエリー中の **東京都** の部分を修正することで他の都道府県のデータにも適用できるかもしれません。

# 3. 解説

## a) 地名を URI に寄せられない事例

前回記事では単純な文字連結によって地名を URI に変換することができました。前回の方法にならうと以下のような SPARQL を作成・実行することでうまくいくようにおもうのですが、これはうまくいきません。

```sparql3.rq
select ?x {
    <http://ja.dbpedia.org/resource/中央区> <http://ja.dbpedia.org/property/外部リンク> ?x .
}
```
実際にこれを実行するとこのように3箇所でエラーが出ます。

![image](https://qiita-image-store.s3.amazonaws.com/0/82494/2e187320-eb9e-e7ac-2b0b-acd07e3fbfd9.png)


中央区は東京に限らず他にもあるので、 <http://ja.dbpedia.org/resource/中央区> は東京の中央区を意味しないからです。


## b) 地名から URI への名寄せ

[GeoNames.jp](http://geonames.jp/) は地名に対応する URI を保持する地名基盤です。次のような形式で地名 URI を保持するという特徴があります。

```geonames.
http://geonames.jp/resource/｛都道府県から始まる省略のない地名｝
```

中央区の場合は以下のような URI になります

* <http://geonames.jp/resource/東京都中央区>

**中央区** というワードに対して <http://ja.dbpedia.org/resource/中央区_(東京都)> という URI を補完するのは想像力やトライ＆エラーが必要ですが、<http://geonames.jp/resource/東京都中央区> であれば比較的補完しやすいのではないでしょうか？


## c) GeoNames.jp から DBpedia Japanese の URI へ

GeoNames.jp の URI と DBpedia Japanese の URI の関係はオープンデータとして公開されています。一例として東京都中央区の場合にはこんなかんじです。

```geonamesjp_links.nt
<http://ja.dbpedia.org/resource/中央区_(東京都)> <http://www.w3.org/2002/07/owl#sameAs> <http://geonames.jp/resource/東京都中央区>
```

この関係は DBpedia Japanese の SPARQL Endpoint に格納されており、 SPARQL を通じて利用することが可能です。次のような SPARQL を実行することで、DBpedia Japanese の URI を得ることができます。

```sparql.rq
select * { ?x <http://www.w3.org/2002/07/owl#sameAs> <http://geonames.jp/resource/東京都中央区>. }
```

## d) SPARQL

以下のような手順で地名を DBpedia Japanese の URI に変換できることがわかります。

1. 地名
2. (文字連結)
3. GeoNames.jp の URI
4. (リンクセット)
5. DBpedia Japanese の URI 

これを踏まえて今回紹介した方法では以下のような SPARQL を使用しています。

```sparql3.rq
select ?x {
    ?s <http://www.w3.org/2002/07/owl#sameAs> <http://geonames.jp/resource/東京都中央区> ;
       <http://ja.dbpedia.org/property/外部リンク> ?x .
}
```

DBpedia Japanese の URI は直接登場せず、 <http://geonames.jp/resource/東京都中央区> という URI が登場していることに注目してください。



# 4. まとめ

* GeoNames.jp の地名URIをキーとして DBpedia Japanese のデータを取得する方法を紹介しました
* SPARQL の記述方法によって、より効率的にデータを取得することが可能です
* （こういった用途が予定される場合には地名とセットで URI が整備されていると便利）


# メモ

DBpedia Japanese の URI と GeoNames.jp の URI 関係は以下のレポジトリで管理されています。

* <https://github.com/dbpedia/links/tree/master/links/xxx.dbpedia.org/ja/geonames.jp>

現時点では都道府県・郡・市区町村に関する関係（リンクセット）が整備されており、DBpedia Japanese の SPARQL Endpoint を通じて使用することができます。