Neo4j 图数据科学 (Graph Data Science, GDS) 基础:图算法
来从头学!对我们来说很容易上手啊,这些数学概念,哈哈哈哈。
目录
官网课程
官网文档
1 算法层和执行模式
这一节介绍不同的算法层级
学完这节你将会
- 了解每个算法层级的意义
- 了解每种算法的执行模式的使用时机
- 知道如何估算在你的数据上运行
GDS 算法所需要的内存
1.1 层级
- 产品质量
: 表示该算法在稳定性和可扩展性方面已经过测试 . 这个层级的算法以gds.<algorithm>为前缀. Beta: 表示该算法是产品质量层的候选算法 . 这个级别的算法前缀为gds.beta.<algorithm>. Alpha: 表示该算法是实验性的 , 可能随时被改变或删除. 本层的算法前缀为gds.alpha.<algorithm>.
1.2 执行模式
stream: 将算法的结果作为一个记录流返回. stats: 返回一条总结性的统计记录, 但不向Neo4j 数据库写入数据或修改任何数据. mutate: 将算法的结果写到内存中的图投影中, 并返回一条总结性的统计记录. write: 将算法的结果写回原Neo4j 数据库, 并返回一条总结性的统计记录.
只有产品质量层的算法才能保证拥有所有执行模式
更多细节以及练习参照
1.3 内存估算
随着数据规模的增长.estimate
只有产品质量层的算法才能保证拥有所有执行模式
更多细节以及练习参照
1.4 一般性算法语法
综合上述内容
CALL gds[.<tier>].<algorithm>.<execution-mode>[.<estimate>](
graphName: STRING,
configuration: MAP
)2 中心性与重要性
中心性算法被用来确定图中不同节点的重要性
中心性的常见使用案例有
- 推荐
: 识别并推荐你提供的产品目录中最有影响力或最受欢迎的项目 - 供应链分析
: 找到你的供应链中最关键的节点 , 比如网络中的供应商, 制造成品的部分原材料, 或者是航线中的一个港口. - 欺诈和异常检测
(anomaly detection) : 寻找有许多共同标识符的用户 , 或在多个社区之间充当桥梁的用户.
2.2 度中心性(degree centrality) 算法实例
度中心性
首先创建图投影
CALL gds.graph.project('proj', ['Actor','Movie'], 'ACTED_IN');然后用stream模式计算度中心性
//get top 5 most prolific actors (those in the most movies)
//using degree centrality which counts number of `ACTED_IN` relationships
CALL gds.degree.stream('proj')
YIELD nodeId, score
RETURN gds.util.asNode(nodeId).name AS actorName, score AS numberOfMoviesActedIn
ORDER BY numberOfMoviesActedIn DESCENDING, actorName LIMIT 5| actorName | numberOfMoviesActedIn |
|---|---|
| Robert De Niro | 56.0 |
| Bruce Willis | 49.0 |
| Nicolas Cage | 45.0 |
| Samuel L. Jackson | 45.0 |
| Clint Eastwood | 40.0 |
前三名演员应该是
2.3 PageRank ( 网页排名) 算法实例
另一种常见的中心性算法是
总的来说
下例应用
首先(Person)-[:DIRECTED_ACTOR]->(Person)的图
//drop last graph projection
CALL gds.graph.drop('proj', false);
//create Cypher projection for network of people directing actors
//filter to recent high grossing movies
CALL gds.graph.project.cypher(
'proj',
'MATCH (a:Person) RETURN id(a) AS id, labels(a) AS labels',
'MATCH (a1:Person)-[:DIRECTED]->(m:Movie)<-[:ACTED_IN]-(a2)
WHERE m.year >= 1990 AND m.revenue >= 10000000
RETURN id(a1) AS source , id(a2) AS target, count(*) AS actedWithCount,
"DIRECTED_ACTOR" AS type'
);接下来用
CALL gds.pageRank.stream('proj')
YIELD nodeId, score
RETURN gds.util.asNode(nodeId).name AS personName, score AS influence
ORDER BY influence DESCENDING, personName LIMIT 5| personName | influence |
|---|---|
| Robert De Niro | 0.6358739386030579 |
| Greg Kinnear | 0.6100648813587659 |
| Sandra Bullock | 0.6091624705383082 |
| Alec Baldwin | 0.5716254867353054 |
| Bruce Willis | 0.5366320764428817 |
前三名演员应该是
2.4 其他中心性算法
其他
- 间隙中心性
(Betweenness Centrality) 算法: 衡量一个节点在图中其他节点之间的程度 . 它经常被用来寻找图的一部分到另一部分的桥梁节点. - 特征向量中心性
(Eigenvector Centrality) 算法: 衡量节点的横向影响力 . 与PageRank 类似, 但只对邻接矩阵(adjacency matrix) 的最大特征向量起作用, 因此不会以同样的方式收敛, 并且更强烈地倾向于度数高的节点. 它在某些特定用例中可能更合适, 特别是不定向关系中. - 文章排名
(Article Rank) 算法: PageRank 算法的变体, 它假定源自低度节点的关系比来自高度节点的关系具有更高的影响力.
完整的产品质量层级的中心性算法列表可以在
3 路径搜索(Path Finding) 算法
路径搜索算法在两个或多个节点之间寻找最短路径
路径搜索的常见用例是
- 供应链分析
: 识别原产地和目的地之间或原材料和成品之间的最快路径 - 客户经历
: 分析构成客户体验的事件 . 例如, 在医疗保健领域一个住院病人从入院到出院的经历.
3.1 Dijkstra 源- 目标最短路径(Dijkstra Source-Target Shortest Path) 算法
一个常见的
下例使用
首先
CALL gds.graph.project('proj',
['Person','Movie'],
{
ACTED_IN:{orientation:'UNDIRECTED'},
DIRECTED:{orientation:'UNDIRECTED'}
}
);然后运行
MATCH (a:Actor)
WHERE a.name IN ['Kevin Bacon', 'Denzel Washington']
WITH collect(id(a)) AS nodeIds
CALL gds.shortestPath.dijkstra.stream('proj', {sourceNode:nodeIds[0], TargetNode:nodeIds[1]})
YIELD sourceNode, targetNode, path
RETURN gds.util.asNode(sourceNode).name AS sourceNodeName,
gds.util.asNode(targetNode).name AS targetNodeName,
nodes(path) as path;这应该会返回一个

3.2 其他路径搜索算法
其他
两个节点之间的最短路径
A* 算法最短路径(A* Shortest Path) : Dijkstra 算法的一个扩展, 使用启发式函数来加快计算速度. - 颜氏算法最短路径
(Yen ’s Algorithm Shortest Path) : Dijkstra 的一个扩展, 允许找到多条最短路径, 即前条最短路径.
一个源节点与多个其他目标节点之间的最短路径
Dijkstra 单源最短路径(Dijkstra Single-Source Shortest Path) : Dijkstra 算法在一个源和多个目标之间最短路径的实现. Delta-Stepping 单源最短路径(Delta-Stepping Single-Source Shortest Path) : 平行的最短路径计算 . 计算速度比Dijkstra 单源最短路径快, 但使用更多内存.
一个源节点与多个其他目标节点之间的一般路径搜索
- 广度优先搜索
(Breadth-First Search, BFS) : 在每次迭代中 , 按照与源节点距离增加的顺序搜索路径. - 深度优先搜索
(Depth First Search, DFS) : 在每次迭代中沿单一多跳路径尽可能地搜索 .
产品层级的中心性算法的完整列表可以在
4 社区检测(Community Detection) 算法
社区检测算法被用来评估节点组在图中的聚类或分区情况
社区检测的常见用例包括
- 欺诈检测
: 通过识别经常发生可疑交易的账户及相互之间共享标识符 , 找到欺诈团伙. - 客户
360: 将多个记录和互动区分为一个单一的客户档案 , 这样一个组织就有了一个关于每个客户信息来源的汇总. - 市场细分
: 根据优先级 , 行为, 兴趣和其他标准, 将目标市场划分为好接触的子群体.
4.1 Louvain 社区检测
一个常见的社区检测算法是

需要注意的是seedProperty参数
下例运行
首先创建一个带有电影UNDIRECTED
CALL gds.graph.project('proj', ['Movie', 'Person'], {
ACTED_IN:{orientation:'UNDIRECTED'},
DIRECTED:{orientation:'UNDIRECTED'}
});然后我们可以运行mutate模式下运行
CALL gds.louvain.mutate('proj', {mutateProperty:'communityId'})我们可以用一个stream操作来验证投影中的communityId节点属性。
CALL gds.graph.streamNodeProperty('proj','communityId', ['Person'])
YIELD nodeId, propertyValue
WITH gds.util.asNode(nodeId) AS n, propertyValue AS communityId
WHERE n:Person
RETURN n.name, communityId LIMIT 5| n.name | communityId |
|---|---|
| François Lallement | 24047 |
| Jules-Eugène Legris | 24047 |
| Lillian Gish | 16346 |
| Mae Marsh | 16346 |
| Henry B. Walthall | 16346 |
4.2 其他社区检测算法
下面是其他一些产品质量层的社区检测算法
-
标签传播
(Label Propagation) : 与 Louvain 算法相似. 是可以很好地并行的快速算法. 对于大型图非常合适. -
弱连接成分
(Weakly Connected Components, WCC) : 将图划分为连接节点的集合 , 以使得-
在同一集合中,任何节点能到达任意其他节点
-
不同集合的节点之间不存在路径
-
-
三角形计数
(Triangle Count) : 计算每个节点的三角形的数量 . 可用于检测社区的凝聚力和图的稳定性. -
局部聚类系数
(Local Clustering Coefficient) : 计算图中每个节点的本地聚类系数 , 这是一个描述该节点与其相邻节点聚集程度的指标.
5 节点嵌入(Node Embedding) 算法
节点嵌入的目标是计算节点的低维向量表示
5.1 直观理解
图

当然
5.2 用例
节点嵌入在多种情况下都有应用
节点嵌入向量本身并不提供见解
- 探索性数据分析
(Exploratory Data Analysis, EDA) 如在 TSNE 图中可视化嵌入,以更好地理解图形结构和潜在的节点集群 - 相似性测量
(Similarity Measurements) : 节点嵌入将使你可以使用 K 近邻算法(KNN) 或其他技术来扩展大型图中的相似性推断. 这对于扩展基于记忆的推荐系统非常有用, 例如协同过滤(collaborative filtering) 的变体. 它还可以用于欺诈检测等领域的半监督技术, 例如, 我们可能想生成与一组已知欺诈实体相似的线索. - 用于机器学习的特征
: 节点嵌入向量可以作为各种机器学习问题的特征 . 例如, 在一个在线零售商的用户购买的关系图中, 我们可以使用嵌入来训练一个机器学习模型, 以预测用户接下来可能有兴趣购买的产品.
5.3 快速随机投影算法(Fast Random Projection, FastRP)
embeddingDimension: 适用于GDS 中的所有节点嵌入算法. 控制嵌入向量的长度. 设置这个参数是对维数和准确性的权衡. 更大的嵌入维度将更准确地捕捉图的结构, 但也需要更长的时间来生成和产生嵌入向量, 需要更多的内存和计算来处理下游. 嵌入维度的选择在很大程度上取决于图中节点的数量. 由于嵌入所能编码的信息量受到其维度的限制, 更大的图将倾向于需要更大的嵌入维度. 典型的取值是128-1024 范围内的2 的次数. 在拥有100K 节点的图形上, 不小于256 的维度能有好的结果. IterationWeights: 控制两个方面: 中间嵌入的迭代次数, 及其对最终节点嵌入的相对影响. 该参数是一个数值列表, 每一个数字表示一次迭代, 数值大小是应用于该迭代的权重. 默认是[0.0, 1.0, 1.0]. 一般而言, 第i次迭代的中间嵌入包含的特征取决于可通过长度为i的路径到达的节点.
还有其他参数可以控制规范化的强度和节点的影响
5.4 FastRP 实例
下例在电影图中的人物节点生成
同样
CALL gds.graph.project('proj', ['Movie', 'Person'], {
ACTED_IN:{orientation:'UNDIRECTED'},
DIRECTED:{orientation:'UNDIRECTED'}
});然后运行randomSeed来控制多次运行之间的一致性
CALL gds.fastRP.stream('proj', {embeddingDimension:64, randomSeed:7474})
YIELD nodeId, embedding
WITH gds.util.asNode(nodeId) AS n, embedding
WHERE n:Person
RETURN id(n), n.name, embedding LIMIT 5| id(n) | n.name | embedding |
|---|---|---|
| 9816 | François Lallement | A list of 64 values. Same below. 长度为 |
| 9817 | Jules-Eugène Legris | |
| 9818 | Lillian Gish | |
| 9819 | Mae Marsh | |
| 9820 | Henry B. Walthall |
理论上
5.5 其他节点嵌入算法
6 相似性算法
相似性算法
类似性算法的常见用例包括
- 欺诈检测
: 通过分析一组新的用户账户与标记账户的相似程度 , 发现潜在的欺诈用户账户 - 推荐系统
: 在网上零售店中 , 识别与用户正在浏览的商品相匹配的商品, 以获得用户印象并提高购买率 - 实体解析
: 根据图中的活动或识别信息,识别出彼此相似的节点
6.1 GDS 中的相似性算法
- 节点相似性
: 根据图中共享的相邻节点的相对比例来确定节点之间的相似性 . 当可解释性很重要时, 节点相似性是一个很好的选择. 你还能把比较范围缩小到数据的一个子集. 缩小范围的例子包括只关注单一社区, 新增加的节点, 或与感兴趣的子图特定距离内的节点. K 近邻算法(KNN) : 基于节点属性来确定相似性 . 如果调整得当, GDS 的KNN 实现可以很好地用于大型图的全局推断. 它可以与嵌入和其他图算法一起使用, 根据图中的接近程度, 节点属性, 社区结构, 重要性/ 中心性等来确定节点之间的相似性.
6.2 度量相似性的选择
节点相似性算法和
6.3 控制比较的范围
将每个节点与图中的其他节点进行比较是一项计算成本很高的工作,其复杂度大约为
节点相似性算法有一个关于节点的degreeCutOff参数
6.4 控制结果的范围
对于相似性比较topK参数来限制每个节点返回的相似性比较的数量
6.5 KNN 算法的应用实例
用之前从节点嵌入中计算出来的嵌入来推断演员和导演之间基于参与过的电影的相似性
CALL gds.graph.project('proj', ['Movie', 'Person'], {
ACTED_IN:{orientation:'UNDIRECTED'},
DIRECTED:{orientation:'UNDIRECTED'}
});然后mutate模式下
CALL gds.fastRP.mutate('proj', {
embeddingDimension:64,
randomSeed:7474,
mutateProperty:'embedding'
})然后我们可以运行相似性算法topK将会限制为
CALL gds.knn.stream('proj', {nodeLabels:['Person'], nodeProperties:['embedding'], topK:1})
YIELD node1, node2, similarity
RETURN gds.util.asNode(node1).name AS actorName1,
gds.util.asNode(node2).name AS actorName2,
similarity
LIMIT 5| actorName1 | actorName2 | similarity |
|---|---|---|
| François Lallement | Giacomo Baessato | 0.7103928923606873 |
| Jules-Eugène Legris | Patrick O’Connell | 0.6735765337944031 |
| Lillian Gish | Mae Marsh | 0.8979091048240662 |
| Mae Marsh | Lillian Gish | 0.8979091048240662 |
| Henry B. Walthall | Mary Alden | 0.6870026588439941 |
6.6 相似性函数
除了节点相似性算法和