Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/neo4j/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Neo4j 使用条件属性创建/设置多个关系属性_Neo4j_Cypher - Fatal编程技术网

Neo4j 使用条件属性创建/设置多个关系属性

Neo4j 使用条件属性创建/设置多个关系属性,neo4j,cypher,Neo4j,Cypher,我试图在加载CSV操作中设置多个关系属性,其中一个属性将始终设置,另一个属性仅在两个节点属于特定标签时设置。我似乎无法让它允许我将多个SET语句链接在一起,它们之间有一个条件 我正试图按照以下思路做一些事情: LOAD CSV WITH HEADERS FROM "file:/smalltext.csv" AS line MATCH (a:Person { username: line.sender }) MATCH (b:Person { username: line.recipient })

我试图在加载CSV操作中设置多个关系属性,其中一个属性将始终设置,另一个属性仅在两个节点属于特定标签时设置。我似乎无法让它允许我将多个SET语句链接在一起,它们之间有一个条件

我正试图按照以下思路做一些事情:

LOAD CSV WITH HEADERS FROM "file:/smalltext.csv" AS line
MATCH (a:Person { username: line.sender })
MATCH (b:Person { username: line.recipient })
CREATE UNIQUE (a)-[r:MSGD ]->(b)
SET r.Msg = coalesce(r.Msg, []) + [line.Msg]
WITH a,b,r, WHERE a:Geotagged AND b:Geotagged,
SET r.Distance = (2 * 6371 * asin(sqrt(haversin(radians(a.statusLat - b.statusLat)) + cos(radians(a.statusLat)) * cos(radians(b.statusLat)) * haversin(radians(a.statusLat - b.statusLon)))));
仅供参考,距离公式直接来自Neo4j,因此我认为它不仅在数学上是正确的,而且在语法上也是正确的

当且仅当两个节点都标记为“地理标记”时,才应设置“距离”特性。原因是,(所有事物的)减法函数不知道如何从数字中减去null(反之亦然),如果用户没有“地理标记”,lat/lon值将为null

我尝试将Msg属性的创建放在CREATE语句中,但它不允许我从relationship属性中引用relationship属性

“地理标签”标签在导入数据时设置(也在加载CSV中),并且仅当每个用户都有地理位置信息时才设置

我还想知道是否应该将距离属性设置为单独的关系?我宁愿把它和信息放在一起,但我也愿意思考这个问题

谢谢

编辑1 如果用户在初始节点创建阶段没有地理标记,我可以将lat/lon设置为0,但是如果不是绝对必须的话,我宁愿不操纵数据

编辑2 在将所有非地理标记节点的LAT和LON设置为0并重新运行关系导入后,Cypher仍然告诉我它无法使用0进行减法(见下文):

QueryExecutionKerneleException:不知道如何 用'33.223'减去(a.statusLat,b.statusLat)'0'`

现在我只是感到困惑…我本以为这不会有问题,但这仍然不是一个好的解决方案,因为当计算地理标记和非地理标记用户之间的距离时,它会给出我无法处理的实际(和错误)结果

编辑3 下面的答案确实有效,但是上面出现异常的原因是因为我试图对字符串进行减法(duh),所以在减法时通过toFloat()运行它们就可以解决这个问题。我尝试运行toFloat()并将结果存储在数据库中,但是如果字段返回NULL,则会完全删除该字段,这不是我想要的行为


如果有人能在同一个加载CSV操作中运行这两个集合,我将非常感激知道如何运行,因为这对于我的实际数据集来说远不是理想的。

我希望这不是一个愚蠢的建议,但是

…将查询拆分为多个部分不是更简单吗?毫无疑问,您不能使用多个Cypher语句以多种方式导入和处理同一个CSV文件。根据您的问题,我假设关系
(a)-[r:MSGD]->(b)
的创建和属性
r.msg
的设置工作正常。当尝试有条件地设置
r.distance
时会出现问题。因此,运行另一个
LOAD CSV
操作,如下所示:

LOAD CSV WITH HEADERS FROM "file:/smalltext.csv" AS line
MATCH (a:Person:Geotagged { username: line.sender })-[r:MSGD]->(b:Person:Geotagged { username: line.recipient })
SET r.Distance = (2 * 6371 * asin(sqrt(haversin(radians(a.statusLat - b.statusLat)) + cos(radians(a.statusLat)) * cos(radians(b.statusLat)) * haversin(radians(a.statusLat - b.statusLon)))));
这应该只匹配那些同时带有
:Person
:geotagated
标签的节点,这些标签由
MSGD
关系链接,因此,只有当两个
Person
节点都带有
geotagated
标签时,才满足设置
r.distance
属性的条件

完整的代码如下所示:

LOAD CSV WITH HEADERS FROM "file:/smalltext.csv" AS line
MATCH (a:Person { username: line.sender })
MATCH (b:Person { username: line.recipient })
CREATE UNIQUE (a)-[r:MSGD]->(b)
SET r.Msg = coalesce(r.Msg, []) + [line.Msg]

LOAD CSV WITH HEADERS FROM "file:/smalltext.csv" AS line
MATCH (a:Person:Geotagged { username: line.sender })-[r:MSGD]->(b:Person:Geotagged { username: line.recipient })
SET r.Distance = (2 * 6371 * asin(sqrt(haversin(radians(a.statusLat - b.statusLat)) + cos(radians(a.statusLat)) * cos(radians(b.statusLat)) * haversin(radians(a.statusLat - b.statusLon)))));

希望这会有帮助。

不,这不是一个愚蠢的建议……我甚至没有考虑过再次阅读该文件。这将使实际数据(300万个节点和数百万个关系)的处理变得更加困难,但是……我仍然认为有一种方法可以在一个语句中完成这一切,但这确实起到了作用。更多细节在我的作品中。