Neo4j 图算法/节点相似度

问题描述

假设下面这张图。

我有一份需要一些技能的工作,通过这份技能列表,我正在寻找的候选人知道这些技能(我的意思是特定工作所需的一组技能)。 这是最简单的部分。

关系具​​有属性 years_of_experience。正确的结果需要 whereCandidate.years_of_experience>= Skill.years_of_experience。 我想使用这样的程序 gds.nodeSimilarity一个候选列表和每个人的相似性。 我可以对这个查询有一些帮助,因为我尝试过但直到现在都没有运气

Graph example

示例:

MATCH aa= (job:JobNode{job_id:'Feed85b9-041c-4bb5-b48a-963c9f927e1d'})-[r:REQUIRES]->(s:SkillNode) 
with job 
MATCH bb= (job:JobNode{job_id:'Feed85b9-041c-4bb5-b48a-963c9f927e1d'})-[r:REQUIRES]->(s:SkillNode)<-[:KNowS]-(c:CandidateNode) 
WITH {item:id(job),categories: collect(id(c))} AS userData 
WITH collect(userData) AS data 
CALL gds.alpha.ml.ann.stream({ data: data,algorithm: 'jaccard' }) 
YIELD item1,item2,similarity 
return data

解决方法

你应该从候选人而不是工作开始。这是因为您正在根据工作所需的技能比较候选人之间的相似性。

MATCH (job:JobNode{job_id:'feed85b9-041c-4bb5-b48a-963c9f927e1d'})-[r:REQUIRES]->(s:SkillNode)<-[:KNOWS]-(c:CandidateNode)
MATCH (c)-[:APPLIED_FOR]-(job)
WITH {item:id(c),categories: collect(id(job))} AS userData
WITH collect(userData) AS data
CALL gds.alpha.ml.ann.stream({
   data: data,algorithm: 'jaccard'
 })
 YIELD item1,item2,similarity
 return gds.util.asNode(item1).name AS Candidate1,gds.util.asNode(item2).name AS Candidate2,similarity
 ORDER BY Candidate1

 Result:
 ╒════════════╤════════════╤════════════╕
 │"Candidate1"│"Candidate2"│"similarity"│
 ╞════════════╪════════════╪════════════╡
 │"Leo"       │"Manos"     │1.0         │
 ├────────────┼────────────┼────────────┤
 │"Manos"     │"Leo"       │1.0         │
 └────────────┴────────────┴────────────┘

编辑: 我认为问题是关于 neo4j 数据科学库中的节点相似性算法。问题是关于计算每个候选人的技能与工作所需的总技能相比的百分比。

步骤:

  1. 获取工作所需的技能总数
  2. 让所有候选人都具备工作所需的技能
  3. 确保该候选人已申请该职位
  4. 返回候选人姓名及其技能除以该职位所需的总技能

注意:函数round(10^2/10^2) 是neo4j 中的一个hack。 Neo4j 不能在桌面上显示小数。如果要保留 3 个小数位,请使用 10^3

MATCH (job:JobNode{job_id:'<id>'})-[:REQUIRES]->(sk:SkillNode)
WITH job,count(sk) as total_skills
MATCH (job)-[r:REQUIRES]->(s:SkillNode)<-[k:KNOWS]-(c:CandidateNode)
MATCH (c)-[:APPLIED_FOR]-(job)
WITH c as candidate,count(s) as skills,total_skills
RETURN candidate.name,round(10^2*skills/total_skills)/10^2 as percent

Result:
╒════════════════╤═════════╕
│"candidate.name"│"percent"│
╞════════════════╪═════════╡
│"Leo"           │0.67     │
├────────────────┼─────────┤
│"Manos"         │0.67     │
└────────────────┴─────────┘