Tag Archives: SPARQL

オントロジーエディタprotégéを使う

2013年10月8日に行われた第7回LinkedData勉強会にて「オントロジーエディタprotégéを使う」と題してprotégéの使い方を簡単に紹介しました。時間がおしていたことなどから非常に駆け足の説明となり、分かりにくい点が多々あったと思います。その後、スライドを見るだけでもなるべく分かるようにするために若干加筆修正をしてslideshareにアップしました。


protégé全体の説明を詳細にすることは困難なので、ひとまず、起動して何をしていいのか分からない、という状況にならないような紹介にしようと思いました。非常に簡単な事例を除いて、最初から思い描いていた通りのオントロジーを構築することはほぼ無理なので、実際の作業としては、オントロジーを作る → それを利用したデータセットを構築する → アプリケーションなどから利用する → 問題を見つける → オントロジーを更新する、の繰り返しが何度か続くことになると思います。なお、今回の資料では推論について全く触れていません。これはprotégéを使い始めるにあたり、推論の知識は必ずしも必要ではないとの判断からです。

また、プロパティの特徴としてFunctional以外については説明を省略しています。これについては、W3CのOWLリファレンスを参照して頂ければと思います。日本語訳もあります。本リファレンスは文字通りOWLについて、プロパティの特徴だけでなく、OWLについて全般的に書かれており、勉強会で紹介したprotégéがOWL2オントロジーをサポートし、Protege-OWLと呼ばれていることも併せて、protégéの提供する編集機能がOWLの仕様と非常によく対応づけられていることが分かります。protégéを利用する際にはこちらを参照するとその操作方法について理解が深まると思います。

参考資料として、スライド中で紹介したもののほかに、古いものもありますが、開発元のサイトに載せられている文書も読んでみると良いと思います。

とはいえ、オントロジーを作るという課題は資料を読むだけでなく、実際に自分で手を動かしてみないと理解しにくいものなのでしょうね。

なお、protégéのダウンロードはここから出来ます。

トリプルストア内の情報を得るサンプルクエリ集

CodeMirrorを使って幾つかのSPARQLクエリのサンプルを列挙してみることにした。

グラフ一覧と各グラフに含まれるトリプル数を取得する
実際にインスタンスをもつクラス一覧と、クラス定義があればその情報も含め、各クラスに含まれるインスタンス数を取得する

トリプルには重複が含まれていることがあるので、念のために distinct を入れている。また、Virtuoso関連クラスを除外するためのフィルタを加えている。

実際に述語としてトリプルを構成する述語一覧と、そのクラス定義があればその情報も含め、各述語が含まれるトリプル数を取得する

なお、ここで使用している distinct * のカウントはVirtuosoでは受け付けられないことが判明したので注意。今後発表されるバージョンでは使えるようになるかもしれない。


今回、相当数のトリプルを検索するSPARQLクエリを様々なエンドポイントに対して試してみたが、実際の結果が得られることは皆無であった。
より検索範囲の小さなものであれば問題無いだろうが、検索対象のデータベースの特徴をある程度ここに掲載したような方法で取得できる統計データなどとともに概観できたほうがより効率的な検索が出来るようになると思う。その他に各クラスの取る代表的な述語や各述語に対する主語や目的語のクラスなども簡単に分かるようになっていると助かる。というのもデータベース提供者以外はそこにあるデータの特徴や構造を通常よく知らないわけなので、どのようなクラスがあり、そこにどれだけのインスタンスがあるかという情報は貴重な参考情報になるからだ。もっともオントロジーがしっかり定義されていたり、voIDなどのデータが用意されていれば、分かることも多いが。また、データ提供者側においても生成されたデータが期待通りになっているのかを確認するため、あるいは、voIDなどのメタデータの生成も含め、得られた情報を予めエンドポイントに表示するためなどの目的で使うと有益だろう。
同様の統計データを取得するSPARQLクエリ集としてこちらのサイトがある。

SPARQL editor test

CodeMirrorを使ったSPARQLクエリのハイライト表示を試すついでに、実際にSPARQLエンドポイントに投げられるようにしてみた。ソースコードは下にある通りで、とても簡単にブログやサイトに埋め込めることから、サンプルクエリを提示する時に使うのも良いと思う。

Endpoint:

<link rel="stylesheet" href="http://codemirror.net/lib/codemirror.css">
<script src="http://codemirror.net/lib/codemirror.js"></script>
<script src="http://codemirror.net/addon/edit/matchbrackets.js"></script>
<script src="http://codemirror.net/mode/sparql/sparql.js"></script>
<style>.CodeMirror {border-top: 1px solid black; border-bottom: 1px solid black;}</style>

<form>Endpoint:<input type="text" size="50" id="epuri"></input><br />
<textarea id="code" name="code"></textarea>
<button type="button" onclick="iq();"><b>Issue Query</b></button></form>
<script>
var editor = CodeMirror.fromTextArea(document.getElementById("code"), {
mode: "application/x-sparql-query",
tabMode: "indent",
matchBrackets: true
});
var iq=function(){
  window.location.assign(document.getElementById("epuri").value+"?query="+encodeURIComponent(editor.getValue()));
}
</script>

SPARQLを使い込む 補足

第5回LinkedData勉強会が先日開かれて「SPARQLを使い込む」と題した発表をさせていただきました。


ここでは発表中に口頭でのみお伝えした点やお伝えしきれなかった点について補足しておきます。
SERVICEキーワードを利用したfederated queriesではリモートのSPARQLエンドポイントに対して容易に大量のデータを返す様なクエリを発行出来てしまいます。従ってこの便利な機能を使う際には、実際にリモートに投げられるクエリを想定して行うのが良いと思います。
クエリの構造として同じスコープにある変数の場合、実際にクエリに書かれている順番にバインドされていくわけではないので、リモートに投げられる時点で、記述したクエリの変数のいずれかがバインドされていることを想定することが出来ません。従って、探索空間が非常に広くなりえることに注意が必要と思います。

SELECT * WHERE {
  ?s ?p ex:obj1213 .
  SERVICE  {
    ?s xe:pred22 ?o .
  }
}

このような場合で、仮に ex:obj1213 を目的語にもつ主語が一つしかなかったとしても、リモートに投げられるクエリには ?s に当該主語がバインドされているとは限らないので、xe:pred22 を述語にもつ全ての主語と目的語の組を探すことになり得ます。

それから、SPARQL1.1で加わった機能のうち、発表中に触れなかった主な項目としてデータベースの更新系があります。CRUDの、Create / Update / Delete が出来るようになっています (参考)。その他、クエリに関しては、以下の機能が1.1になり新たに加わっています (参考)。

このうち、まず、Aggregatesについては、数値処理の集合演算であるCOUNTSUMなどを除いて紹介していませんが、これらに加え、SQLでお馴染みのGROUP BYHAVINGが使えるようになっています。
また、一つのクエリ表現で複数の述語にマッチさせられる表記法法、Property Pathsについて全く触れておりません。これについては去年の第2回LinkedData勉強会で加藤さんがSPARQLの基礎と題して説明されていますのでご参照願います。
その他、CONSTRUCTの短縮表現についても扱っていません。これはCONSTRUCT WHEREと記述するもので、CONSTRUCTキーワード後のグラフパターンを省略出来る表現方法です。これは、WHERE直後のグラフパターンが単純であるときに使えます。つまり、FILTERキーワードや複雑なグラフパターンが含まれてなく、そのパターンがそのままトリプルとして取り出せる様なクエリであることが条件になります。詳細は上記リンク先をご確認ください。