2015-10-05 89 views
0

有没有办法使用Java API来访问OrientDB中的边缘索引,以确定在两个已知顶点之间是否存在具有给定标签的边?通过Java的OrientDB边缘索引

Afaik tinkergraph没有公开任何方法吗?

我相信,Neo4j的是提供了一个API是这样的:

graphDatabaseService.index().forRelationships("HAS_USER").get(key, valueOrNull, startNodeOrNull, endNodeOrNull) 

回答

2

你可以从你的顶点调用getEdges()。例如:

v1.getEdges(v2, Direction.BOTH, "HAS_USER"); 

这是的JavaDoc:

/** 
    * (Blueprints Extension) Returns all the edges from the current Vertex to another one. 
    * 
    * @param iDestination 
    *   The target vertex 
    * @param iDirection 
    *   The direction between OUT, IN or BOTH 
    * @param iLabels 
    *   Optional labels as Strings to consider 
    * @return 
    */ 
    public Iterable<Edge> getEdges(final OrientVertex iDestination, final Direction iDirection, final String... iLabels) 
+0

我不想一个独特优势创建索引。我想确定两个已知顶点之间是否存在具有给定标签的边。 – Jotschi

+0

更新了我的答案。 – Lvca

0

的另一种方法是使用OrientGraph.getEdges()

创建索引是很重要的第一通路:

cmd.setText("create index edge.HAS_ITEM on E (out,in) unique"); 
g.command(cmd).execute(); 

或经由纯Java:

OrientEdgeType e = g.getEdgeType("E"); 
e.createProperty("in", OType.LINK); 
e.createProperty("out", OType.LINK); 
e.createIndex("edge.has_item", OClass.INDEX_TYPE.UNIQUE_HASH_INDEX, "out", "in"); 

在此之后,索引可以使用查询:

Iterable<Edge> edges = g.getEdges("edge.has_item", new OCompositeKey(root.getId(), randomDocument.getId())); 

小pittfall:在getEdges方法引用时,它为小写索引类型是重要的。否则orientdb将无法检索它。

下面列出了一个完整的示例,其中显示了在两个顶点之间找到特定边的四种方法。

在该示例中,创建了14k个连接到单个根节点的顶点(项目)。

Creating {14000} items. 
[graph.getEdges] Duration: 38 
[graph.getEdges] Duration per lookup: 0.0095 

[root.getEdges] Duration: 59439 
[root.getEdges] Duration per lookup: 14.85975 

[root.getEdges - iterating] Duration: 56710 
[root.getEdges - iterating] Duration per lookup: 14.1775 

[query] Duration: 817 
[query] Duration per lookup: 0.20425 

例子:

package de.jotschi.orientdb; 

import static org.junit.Assert.assertTrue; 

import java.util.ArrayList; 
import java.util.List; 

import org.junit.BeforeClass; 
import org.junit.Test; 

import com.orientechnologies.orient.core.index.OCompositeKey; 
import com.orientechnologies.orient.core.metadata.schema.OType; 
import com.orientechnologies.orient.core.sql.OCommandSQL; 
import com.tinkerpop.blueprints.Direction; 
import com.tinkerpop.blueprints.Edge; 
import com.tinkerpop.blueprints.Vertex; 
import com.tinkerpop.blueprints.impls.orient.OrientEdgeType; 
import com.tinkerpop.blueprints.impls.orient.OrientGraphFactory; 
import com.tinkerpop.blueprints.impls.orient.OrientGraphNoTx; 
import com.tinkerpop.blueprints.impls.orient.OrientVertex; 
import com.tinkerpop.blueprints.impls.orient.OrientVertexType; 

public class EdgeIndexPerformanceTest { 

    private static OrientGraphFactory factory = new OrientGraphFactory("memory:tinkerpop"); 

    private final static int nDocuments = 14000; 
    private final static int nChecks = 4000; 

    private static List<OrientVertex> items; 
    private static OrientVertex root; 

    @BeforeClass 
    public static void setupDatabase() { 
     setupTypesAndIndices(factory); 

     root = createRoot(factory); 
     items = createData(root, factory, nDocuments); 
    } 

    private static void setupTypesAndIndices(OrientGraphFactory factory2) { 
     OrientGraphNoTx g = factory.getNoTx(); 
     try { 
      OCommandSQL cmd = new OCommandSQL(); 

      cmd.setText("alter database custom useLightweightEdges=false"); 
      g.command(cmd).execute(); 

      cmd.setText("alter database custom useVertexFieldsForEdgeLabels=false"); 
      g.command(cmd).execute(); 

      OrientEdgeType e = g.getEdgeType("E"); 
      e.createProperty("in", OType.LINK); 
      e.createProperty("out", OType.LINK); 

      OrientVertexType v = g.createVertexType("root", "V"); 
      v.createProperty("name", OType.STRING); 

      v = g.createVertexType("item", "V"); 
      v.createProperty("name", OType.STRING); 

      cmd.setText("create index edge.HAS_ITEM on E (out,in) unique"); 
      g.command(cmd).execute(); 

     } finally { 
      g.shutdown(); 
     } 

    } 

    private static List<OrientVertex> createData(OrientVertex root, OrientGraphFactory factory, int count) { 
     OrientGraphNoTx g = factory.getNoTx(); 
     try { 
      System.out.println("Creating {" + count + "} items."); 
      List<OrientVertex> items = new ArrayList<>(); 
      for (int i = 0; i < count; i++) { 
       OrientVertex item = g.addVertex("class:item"); 
       item.setProperty("name", "item_" + i); 
       items.add(item); 
       root.addEdge("HAS_ITEM", item, "class:E"); 
      } 
      return items; 
     } finally { 
      g.shutdown(); 
     } 
    } 

    private static OrientVertex createRoot(OrientGraphFactory factory) { 
     OrientGraphNoTx g = factory.getNoTx(); 
     try { 
      OrientVertex root = g.addVertex("class:root"); 
      root.setProperty("name", "root vertex"); 
      return root; 
     } finally { 
      g.shutdown(); 
     } 
    } 

    @Test 
    public void testEdgeIndexViaRootGetEdgesWithoutTarget() throws Exception { 
     OrientGraphNoTx g = factory.getNoTx(); 
     try { 
      long start = System.currentTimeMillis(); 
      for (int i = 0; i < nChecks; i++) { 
       OrientVertex randomDocument = items.get((int) (Math.random() * items.size())); 
       Iterable<Edge> edges = root.getEdges(Direction.OUT, "HAS_ITEM"); 
       boolean found = false; 
       for (Edge edge : edges) { 
        if (edge.getVertex(Direction.IN).equals(randomDocument)) { 
         found = true; 
         break; 
        } 
       } 
       assertTrue(found); 
      } 
      long dur = System.currentTimeMillis() - start; 
      System.out.println("[root.getEdges - iterating] Duration: " + dur); 
      System.out.println("[root.getEdges - iterating] Duration per lookup: " + ((double) dur/(double) nChecks)); 
     } finally { 
      g.shutdown(); 
     } 
    } 

    @Test 
    public void testEdgeIndexViaRootGetEdges() throws Exception { 
     OrientGraphNoTx g = factory.getNoTx(); 
     try { 
      long start = System.currentTimeMillis(); 
      for (int i = 0; i < nChecks; i++) { 
       OrientVertex randomDocument = items.get((int) (Math.random() * items.size())); 
       Iterable<Edge> edges = root.getEdges(randomDocument, Direction.OUT, "HAS_ITEM"); 
       assertTrue(edges.iterator().hasNext()); 
      } 
      long dur = System.currentTimeMillis() - start; 
      System.out.println("[root.getEdges] Duration: " + dur); 
      System.out.println("[root.getEdges] Duration per lookup: " + ((double) dur/(double) nChecks)); 
     } finally { 
      g.shutdown(); 
     } 
    } 

    @Test 
    public void testEdgeIndexViaGraphGetEdges() throws Exception { 
     OrientGraphNoTx g = factory.getNoTx(); 
     try { 
      long start = System.currentTimeMillis(); 
      for (int i = 0; i < nChecks; i++) { 
       OrientVertex randomDocument = items.get((int) (Math.random() * items.size())); 
       Iterable<Edge> edges = g.getEdges("edge.has_item", new OCompositeKey(root.getId(), randomDocument.getId())); 
       assertTrue(edges.iterator().hasNext()); 
      } 
      long dur = System.currentTimeMillis() - start; 
      System.out.println("[graph.getEdges] Duration: " + dur); 
      System.out.println("[graph.getEdges] Duration per lookup: " + ((double) dur/(double) nChecks)); 
     } finally { 
      g.shutdown(); 
     } 
    } 

    @Test 
    public void testEdgeIndexViaQuery() throws Exception { 
     OrientGraphNoTx g = factory.getNoTx(); 
     try { 
      System.out.println("Checking edge"); 
      long start = System.currentTimeMillis(); 
      for (int i = 0; i < nChecks; i++) { 
       OrientVertex randomDocument = items.get((int) (Math.random() * items.size())); 

       OCommandSQL cmd = new OCommandSQL("select from index:edge.has_item where key=?"); 
       OCompositeKey key = new OCompositeKey(root.getId(), randomDocument.getId()); 

       assertTrue(((Iterable<Vertex>) g.command(cmd).execute(key)).iterator().hasNext()); 
      } 
      long dur = System.currentTimeMillis() - start; 
      System.out.println("[query] Duration: " + dur); 
      System.out.println("[query] Duration per lookup: " + ((double) dur/(double) nChecks)); 
     } finally { 
      g.shutdown(); 
     } 
    } 

}