首页 文章

neo4j用于欺诈检测 - 高效的数据结构

提问于
浏览
0

我正在努力改进商业网站的欺诈检测系统 . 我们处理直接银行交易,因此欺诈是我们需要管理的风险 . 我最近了解了图形数据库,并可以看到它如何应用于这些问题 . 所以,在过去的几天里,我设置了neo4j并将我们的数据解析为:example

我的直觉是为每个订单创建一个节点,为每个订单创建一个节点,然后将它们连接在一起 . 像这样:

MATCH (w:Wallet),(i:Ip),(e:Email),(o:Order) 
WHERE w.wallet="ex" AND i.ip="ex" AND e.email="ex" AND o.refcode="ex" 
CREATE (w)-[:USED]->(o),(i)-[:USED]->(o),(e)-[:USED]->(o)

但是随着数据库大小的增加,这个查询运行得非常慢(我假设它需要搜索我要求的节点的整个数据集) . 运行这样的查询也需要很长时间:

START a=node(179) 
MATCH (a)-[:USED*]-(d) 
WHERE EXISTS(d.refcode) 
RETURN distinct d

这旨在提取连接到起点的所有订单 . 我是Cypher的新手(<24小时),我发现寻找解决方案特别困难 .

我可以解决的数据结构或查询是否存在任何特定问题以提高性能?理想情况下,它需要在几秒钟内完成这类事情,正如我对SQL数据库的期望 . 目前我们有大约17,000个节点 .

1 回答

  • 0

    始终是一个好主意,完全阅读developers manual .

    为了加速属性对节点的查找,您肯定需要创建indexes or unique constraints(取决于属性是否应对标签/值唯一) .

    一旦您创建了所需的索引和约束,它们将在您的查询中用于加速您的匹配 .

    START仅用于旧版索引,对于最新的Neo4j版本,您应该使用MATCH . 如果您根据内部ID进行匹配,则可以使用 MATCH (n) WHERE id(n) = xxx .

    请记住,您不应该在Neo4j之外保留节点ID以便在将来的查询中进行查找,因为内部节点ID可以在删除和创建节点时重复使用,因此曾经引用已被删除的节点的ID可能稍后会指向到一个完全不同的节点 .

    在查询中使用标签可以帮助您提高性能 . 在您查找订单的查询中,Neo4j必须检查路径中的每个终端节点以查看该属性是否存在 . 属性访问往往很昂贵,尤其是当您使用可变长度匹配时,因此最好通过标签限制所需的节点 .

    MATCH (a)-[:USED*]-(d:Order)
    WHERE id(a) = 179 
    RETURN distinct d
    

    在较大的图形上,可变长度匹配可能开始减慢,因此您可以通过安装APOC Procedures并使用Path Expander过程来收集所有子图节点并过滤到只有Order节点来获得更高的性能 .

    MATCH (a)
    WHERE id(a) = 179
    CALL apoc.path.expandConfig(a, {bfs:true, uniqueness:"NODE_GLOBAL"}) YIELD path
    RETURN LAST(NODES(path)) as d
    WHERE d:Order
    

相关问题