リレーションの表現
ノード間の関連を表すにはRelationshipオブジェクトを用いる。図2のような簡単な関連を考えてみよう。
図2 リレーションの例 |
上手の関連を定義するコード例を以下に示す。Relationshipオブジェクトにはノードと同様に任意のプロパティを設定することができるため、関連を定義するだけでなく、付加的な情報を持たせることも可能だ。
// 関連のタイプを表現する列挙型
public enum MyRelationshipTypes implements RelationshipType {
WORKS_AT
}
...
// 1つめのノードを作成
Node person = graphDb.createNode();
person.setProperty("name", "Naoki Takezoe");
// 2つめのノードを作成
Node company = graphDb.createNode();
company.setProperty("name", "NTT DATA INTELLILINK");
// 1つめのノードから2つめのノードへの関連を定義
Relationship relationship = person.createRelationshipTo(company, MyRelationshipTypes.WORKS_AT);
relationship.setProperty("message", "Hello neo4j!");
ノードの検索
続いてノードを検索する方法をみてみよう。neo4jでは以下のような検索手段が用意されている。
- すべてのノードをIteratorで取得
- IDを指定して特定のノードを取得
- Traverserを使用した検索
この中でも特に利用頻度が高く重要なのがTraverserを使用した検索だ。基点となるノードを取得し、Node#traverse()メソッドを呼び出すことで関連を持つノードをトラバースすることができる。トラバースを行うコードの例を以下に示す。
// 基点となるノードを取得
Node company = ...
// MyRelationshipTypes.EMPLOYSの関連をたどるトラバーサ
Traverser traverser = company.traverse(
Order.DEPTH_FIRST,
StopEvaluator.END_OF_GRAPH,
ReturnableEvaluator.ALL_BUT_START_NODE,
MyRelationshipTypes.EMPLOYS,
Direction.OUTGOING);
for(Node employee: traverser){
...
}
上記の例ではMyRelationshipTypes.EMPLOYSの関連をたどっているが、ReturnableEvaluatorを拡張することでその他の条件を付加することができる。以下の例ではMyRelationshipTypes.EMPLOYSの関連をたどり、roleプロパティがEngineerのノードを返却するTraverserを取得している。
Traverser traverser = startNode.traverse(
Order.DEPTH_FIRST,
StopEvaluator.END_OF_GRAPH,
new ReturnableEvaluator() {
@Override
public boolean isReturnableNode(TraversalPosition pos) {
return pos.currentNode().getProperty("role").equals("Engineer");
}
},
MyRelationshipTypes.EMPLOYS,
Direction.OUTGOING);
このようにneo4jで検索を行うにはノード間のリレーションの設計とTraverserの使い方が重要なポイントになってくる。