0

2000 ノードを挿入すると、10000 ミリ秒が消費されます。これは私が試しているコードです:

package org.demo.neo4j;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Semaphore;
import java.util.logging.Level;
import java.util.logging.Logger;
import org.neo4j.graphdb.Direction;
import org.neo4j.graphdb.DynamicRelationshipType;
import org.neo4j.graphdb.GraphDatabaseService;
import org.neo4j.graphdb.Node;
import org.neo4j.graphdb.Relationship;
import org.neo4j.graphdb.RelationshipType;
import org.neo4j.graphdb.Transaction;

public class Main {

    private GraphDatabaseService neo = Noe4jUtils.getInstance();
    private static ExecutorService pool = Executors.newFixedThreadPool(4);
    private static Semaphore semaphore = new Semaphore(4);

    public static void main(String[] args) {
        Main main = new Main();
        main.insert();
    }

    private void insert() {
        for (int i = 0; i < 1000; i++) {
            try {
                semaphore.acquire();
                String refName = "REF-" + i;
                pool.execute(new InsertTask(refName, 100000));
            } catch (InterruptedException ex) {
                Logger.getLogger(Main.class.getName()).log(Level.SEVERE, null, ex);
            }
        }
    }

    private void insertRef(String refName, int num) {
        Node rootNode = neo.getReferenceNode();
        RelationshipType rt = DynamicRelationshipType.withName(refName);
        Relationship r = rootNode.getSingleRelationship(rt, Direction.OUTGOING);
        Node refNode;
        if (null == r) {
            refNode = createRef(rootNode, rt);
        } else {
            refNode = r.getOtherNode(rootNode);
        }
        int size = 2000;
        int cnt = num / size;
        if ((num % size) != 0) {
            cnt = cnt + 1;
        }
        int index = 0;
        for (int i = 0; i < cnt; i++) {
            long l1 = System.currentTimeMillis();
            Transaction tx = neo.beginTx();
            try {
                int tmpNum = 0;
                for (int j = 0; j < size; j++) {
                    index++;
                    if (index > num) {
                        break;
                    }
                    tmpNum++;
                    createNode(refNode);
                }
                tx.success();
                System.out.println("insert " + tmpNum + " node.");
            } finally {
                tx.finish();
                l1 = System.currentTimeMillis() - l1;
                System.out.println("consume " + l1 + " ms.");
            }
        }
    }

    private Node createRef(Node node, RelationshipType rt) {
        Transaction tx = neo.beginTx();
        try {
            Node tmpNode = node.getGraphDatabase().createNode();
            node.createRelationshipTo(tmpNode, rt);
            tx.success();
            return tmpNode;
        } finally {
            tx.finish();
        }
    }

    private Node createNode(Node node) {
        RelationshipType rt = DynamicRelationshipType.withName("LINK");
        Node tmpNode = node.getGraphDatabase().createNode();
        node.createRelationshipTo(tmpNode, rt);
        for (int i = 0; i < 100; i++) {
            tmpNode.setProperty("key" + i, i);
        }
        return node;
    }

    class InsertTask implements Runnable {

        public InsertTask(String refName, int num) {
            this.refName = refName;
            this.num = num;
        }
        private String refName;
        private int num;

        @Override
        public void run() {
            try {
                insertRef(refName, num);
            } finally {
                semaphore.release();
            }
        }
    } }
4

2 に答える 2

2

これらの小さなトランザクションを作成する目的は何ですか? neo4j の各トランザクションは論理ログを強制的にディスクに書き込むため、基本的にすべての時間がディスクのフラッシュを待つことに費やされます。そのため、複数のスレッドはそれほど役に立ちません。逆に、遅くなる可能性があります。各トランザクションではなく、多くの操作をグループ化し、スレッドを 1 つにするようにしてください。

ところで、あなたのユースケースは何ですか?

于 2012-07-05T19:24:18.290 に答える
-1

これを Linux の ext4 ファイルシステムで実行していますか?

少しのトランザクションの安全性と引き換えに 10 ~ 15 倍の書き込みパフォーマンスを向上させたい場合は、http://structr.org/blog/neo4j-performance-on-ext4 で説明されているように、barrier=0 オプションを試してください。

于 2013-12-11T00:46:52.310 に答える