我目前正在探索行业中某些流程的图形数据库潜力。 我一周前开始使用Neo4Jclient,所以我低于标准初学者: - )
我对Neo4J感到非常兴奋,但我面临巨大的表演问题,我需要帮助。
我的项目的第一步是从现有的文本文件中填充Neo4j。 这些文件由使用简单模式格式化的行组成:
StringID=StringLabel(String1,String2,...,StringN);
例如,如果我考虑以下行:
#126=TYPE1(#80,#125);
我想创建一个带有标签" TYPE1"和2个属性的节点: 1)使用ObjectID的唯一ID:"#126"在上面的例子中 2)包含所有参数以供将来使用的字符串:"#80,#125"在上面的例子中
我必须考虑我将处理多个前向引用,如下例所示:
#153=TYPE22('0BTBFw6f90Nfh9rP1dl_3P',#144,#6289,$);
用StringID"#6289"定义节点的行。将在文件中稍后解析。
因此,为了解决我的文件导入问题,我已经定义了以下类:
public class myEntity
{
public string propID { get; set; }
public string propATTR { get; set; }
public myEntity()
{
}
}
感谢我的文本文件中的前向引用(毫无疑问,我的Neo4J知识很差......) 我决定分3个步骤开展工作:
我从我的文件解析的每一行中提取第一个循环,strLABEL,strID和strATTRIBUTES, 然后我使用以下代码为每一行添加一个Neo4j节点:
strLabel = "(entity:" + strLABEL + " { propID: {newEntity}.propID })";
graphClient.Cypher
.Merge(strLabel)
.OnCreate()
.Set("entity = {newEntity}")
.WithParams(new {
newEntity = new {
propID = strID,
propATTR = strATTRIBUTES
}
})
.ExecuteWithoutResults();
然后我使用以下代码匹配在Neo4J中创建的所有节点:
var queryNode = graphClient.Cypher
.Match("(nodes)")
.Return(nodes => new {
NodeEntity = nodes.As<myEntity>(),
Labels = nodes.Labels()
}
);
最后我在所有节点上循环,拆分每个节点的propATTR属性,并使用以下代码为propATTR中找到的每个ObjectID添加一个关系:
graphClient.Cypher
.Match("(myEnt1)", "(myEnt2)")
.Where((myEntity myEnt1) => myEnt1.propID == strID)
.AndWhere((myEntity myEnt2) => myEnt2.propID == matchAttr)
.CreateUnique("myEnt1-[:INTOUCHWITH]->myEnt2")
.ExecuteWithoutResults();
当我使用Cypher探索使用该代码填充的数据库时,生成的节点和关系是正确的,并且Neo4J执行速度非常快,我已经测试过任何查询。 它令人印象深刻,我深信Neo4j在我的行业中有着巨大的潜力。
但是我今天的大问题是填充数据库所需的时间(我的配置:win8 x64,32Go RAM,SSD,intel core i7-3840QM 2.8GHz):
对于小型测试用例(6400行) 我花了13s创建了6373个节点,94s创建了7800个节点
在一个真实的测试用例(40000行) 它带我496s创建38898个节点,3701s创建89532个关系(是的:超过一个小时!)
毫无疑问,这种糟糕的表现直接源于我糟糕的新知识。
如果社区可以告诉我如何解决这个瓶颈,对我来说将是一个巨大的帮助。
感谢您的帮助。
祝你好运 最大
答案 0 :(得分:0)
虽然我脑子里没有确切的语法可以为你写下来,但我建议你先看一下你的propATTR值,然后将它们作为数组/集合直接存储在Neo4j中。 。这有望使您能够在Neo4j中批量创建关系,而不是在外部迭代节点并执行如此多的顺序事务。
后一部分可能类似于:
MATCH (myEnt1),(myEnt2) WHERE myEnt1.propID IN myEnt2.propATTR
CREATE UNIQUE (myEnt1)-[:INTOUCHWITH]->(myEnt2)
抱歉,我的Cypher有点生疏,但重点是尝试将负载完全转移到Neo4j引擎,而不是应用程序逻辑和Neo4j服务器之间的连续往返。我建议这些往返行程可能会影响您的表现,而不是每项交易所涉及的个人工作,所以最大限度地减少交易次数是可行的。