当前位置: 首页 > 知识库问答 >
问题:

Neo4j SDN 4图形性能与指数

滕翔飞
2023-03-14

在我的Neo4j/SDN 4应用程序中,我的所有密码查询都基于内部Neo4j ID。

这是一个问题,因为我不能在我的web应用程序URL上依赖这些ID。Neo4j可以重用这些ID,因此很有可能在将来的某个时候,在相同的ID下,我们可以找到另一个节点。

我尝试基于以下解决方案重新实现此逻辑:使用图控制唯一id的生成,但发现查询性能下降。

从理论上看,基于@Index(unique=true,primary=true)属性的密码查询是否应该

例如:

@Index(unique = true, primary = true)
private Long uid;

entity.uid = {someId}

与基于内部Neo4j ID的Cypher查询具有相同的性能:

id(entity) = {someId} 

更新

这是:模式输出:

Indexes
   ON :BaseEntity(uid) ONLINE
   ON :Characteristic(lowerName) ONLINE
   ON :CharacteristicGroup(lowerName) ONLINE
   ON :Criterion(lowerName) ONLINE
   ON :CriterionGroup(lowerName) ONLINE
   ON :Decision(lowerName) ONLINE
   ON :FlagType(name) ONLINE (for uniqueness constraint)
   ON :HAS_VALUE_ON(value) ONLINE
   ON :HistoryValue(originalValue) ONLINE
   ON :Permission(code) ONLINE (for uniqueness constraint)
   ON :Role(name) ONLINE (for uniqueness constraint)
   ON :User(email) ONLINE (for uniqueness constraint)
   ON :User(username) ONLINE (for uniqueness constraint)
   ON :Value(value) ONLINE

Constraints
   ON ( flagtype:FlagType ) ASSERT flagtype.name IS UNIQUE
   ON ( permission:Permission ) ASSERT permission.code IS UNIQUE
   ON ( role:Role ) ASSERT role.name IS UNIQUE
   ON ( user:User ) ASSERT user.email IS UNIQUE
   ON ( user:User ) ASSERT user.username IS UNIQUE

如您所见,我在:BaseEntity(uid)

BaseEntity是我的实体层次结构中的基类,例如:

@NodeEntity
public abstract class BaseEntity {

    @GraphId
    private Long id;

    @Index(unique = false)
    private Long uid;

    private Date createDate;

    private Date updateDate;

...

}

@NodeEntity
public class Commentable extends BaseEntity {
...
}

@NodeEntity
public class Decision extends Commentable {

    private String name;

}

这个uid索引是否会在我查找(d:Decision)的示例时使用,其中d.uid={uid}

PROFILE结果-内部ID vs索引属性

基于内部ID的查询

PROFILE MATCH (parentD)-[:CONTAINS]->(childD:Decision) 
WHERE id(parentD) = 1474333 
MATCH (childD)-[relationshipValueRel1475199:HAS_VALUE_ON]-(filterCharacteristic1475199) 
WHERE id(filterCharacteristic1475199) = 1475199 
WITH relationshipValueRel1475199, childD 
WHERE  ([1, 19][0] <= relationshipValueRel1475199.value <=  [1, 19][1] )  
WITH childD  
MATCH (childD)-[relationshipValueRel1474358:HAS_VALUE_ON]-(filterCharacteristic1474358) 
WHERE id(filterCharacteristic1474358) = 1474358 
WITH relationshipValueRel1474358, childD 
WHERE  (ANY (id IN ['Compact'] WHERE id IN relationshipValueRel1474358.value ))  
WITH childD  
MATCH (childD)-[relationshipValueRel1475193:HAS_VALUE_ON]-(filterCharacteristic1475193) 
WHERE id(filterCharacteristic1475193) = 1475193 
WITH relationshipValueRel1475193, childD 
WHERE  (ANY (id IN ['16:9', '3:2', '4:3', '1:1'] 
WHERE id IN relationshipValueRel1475193.value ))  
WITH childD  
OPTIONAL MATCH (childD)-[vg:HAS_VOTE_ON]->(c) 
WHERE id(c) IN [1474342, 1474343, 1474340, 1474339, 1474336, 1474352, 1474353, 1474350, 1474351, 1474348, 1474346, 1474344] 
WITH childD, vg.avgVotesWeight as weight, vg.totalVotes as totalVotes 
WITH * MATCH (childD)-[ru:CREATED_BY]->(u:User)  
WITH ru, u, childD , toFloat(sum(weight)) as weight, toInt(sum(totalVotes)) as totalVotes  
ORDER BY  weight DESC 
SKIP 0 LIMIT 10 
RETURN ru, u, childD AS decision, weight, totalVotes, 
[ (parentD)<-[:DEFINED_BY]-(entity)<-[:COMMENTED_ON]-(comg:CommentGroup)-[:COMMENTED_FOR]->(childD) | {entityId: id(entity),  types: labels(entity), totalComments: toInt(comg.totalComments)} ] AS commentGroups, 
[ (parentD)<-[:DEFINED_BY]-(c1)<-[vg1:HAS_VOTE_ON]-(childD) | {criterionId: id(c1),  weight: vg1.avgVotesWeight, totalVotes: toInt(vg1.totalVotes)} ] AS weightedCriteria, 
[ (parentD)<-[:DEFINED_BY]-(ch1:Characteristic)<-[v1:HAS_VALUE_ON]-(childD)  WHERE NOT ((ch1)<-[:DEPENDS_ON]-())  | {characteristicId: id(ch1),  value: v1.value, totalHistoryValues: toInt(v1.totalHistoryValues), description: v1.description, valueType: ch1.valueType, visualMode: ch1.visualMode} ] AS valuedCharacteristics

PROFILE输出:

Cypher版本:CYPHER 3.1,计划程序:成本,运行时:解释。

基于索引属性uid的查询

PROFILE MATCH (parentD)-[:CONTAINS]->(childD:Decision) 
WHERE parentD.uid = 61 
MATCH (childD)-[relationshipValueRel1475199:HAS_VALUE_ON]-(filterCharacteristic1475199) 
WHERE filterCharacteristic1475199.uid = 15 
WITH relationshipValueRel1475199, childD 
WHERE  ([1, 19][0] <= relationshipValueRel1475199.value <=  [1, 19][1] )  
WITH childD  
MATCH (childD)-[relationshipValueRel1474358:HAS_VALUE_ON]-(filterCharacteristic1474358) 
WHERE filterCharacteristic1474358.uid = 10 
WITH relationshipValueRel1474358, childD 
WHERE  (ANY (id IN ['Compact'] WHERE id IN relationshipValueRel1474358.value ))  
WITH childD  
MATCH (childD)-[relationshipValueRel1475193:HAS_VALUE_ON]-(filterCharacteristic1475193) 
WHERE filterCharacteristic1475193.uid = 14 
WITH relationshipValueRel1475193, childD 
WHERE  (ANY (id IN ['16:9', '3:2', '4:3', '1:1'] 
WHERE id IN relationshipValueRel1475193.value ))  
WITH childD  
OPTIONAL MATCH (childD)-[vg:HAS_VOTE_ON]->(c) 
WHERE c.uid IN [26, 27, 24, 23, 20, 36, 37, 34, 35, 32, 30, 28] 
WITH childD, vg.avgVotesWeight as weight, vg.totalVotes as totalVotes 
WITH * MATCH (childD)-[ru:CREATED_BY]->(u:User)  
WITH ru, u, childD , toFloat(sum(weight)) as weight, toInt(sum(totalVotes)) as totalVotes  
ORDER BY  weight DESC 
SKIP 0 LIMIT 10 
RETURN ru, u, childD AS decision, weight, totalVotes, 
[ (parentD)<-[:DEFINED_BY]-(entity)<-[:COMMENTED_ON]-(comg:CommentGroup)-[:COMMENTED_FOR]->(childD) | {entityId: id(entity),  types: labels(entity), totalComments: toInt(comg.totalComments)} ] AS commentGroups, 
[ (parentD)<-[:DEFINED_BY]-(c1)<-[vg1:HAS_VOTE_ON]-(childD) | {criterionId: id(c1),  weight: vg1.avgVotesWeight, totalVotes: toInt(vg1.totalVotes)} ] AS weightedCriteria, 
[ (parentD)<-[:DEFINED_BY]-(ch1:Characteristic)<-[v1:HAS_VALUE_ON]-(childD)  WHERE NOT ((ch1)<-[:DEPENDS_ON]-())  | {characteristicId: id(ch1),  value: v1.value, totalHistoryValues: toInt(v1.totalHistoryValues), description: v1.description, valueType: ch1.valueType, visualMode: ch1.visualMode} ] AS valuedCharacteristics

密码版本:密码3.1,计划员:成本,运行时:解释。426毫秒内总命中数为671326分贝。

有没有机会提高基于uid的性能?

共有1个答案

田成仁
2023-03-14

你是正确的不使用Neo4j内部id在web网址,因为他们可以重用后,节点被删除等。

从性能的角度来看,内部id是尽可能快的-它实际上是一个偏移文件与节点/关系记录(你可能已经注意到这是2个独立的id序列,你可以有id=z的节点和相同id=的关系X)。

索引的任何使用都必须较慢,因为数据库首先进行索引查找,获取内部id,然后读取节点记录。

然而,对于绝大多数应用程序来说,性能上的差异可以忽略不计——可能比网络延迟或一般OGM开销小得多。

如果你看到明显的不同

  • 验证数据库中是否存在索引(例如Neo4j浏览器中的:schema
  • 打开日志记录并验证您的查询是否具有正确的标签(为org.neo4j.ogm设置info级别)
  • 如果索引存在且查询包含右标签,则使用PROFILE检查查询计划

更新

是,索引将用于以下查询:

MATCH (d:Decision) WHERE d.uid = {uid} ...

应该由

session.load(Decision.class, uid)

如果您的索引是主索引或findByUid决策存储库上。

注意,当WHERE子句出现在查询的中间时,索引可能不被使用:

...
WITH x
MATCH (x)-[...]-(d) WHERE d.uid = {uid} ...

这取决于查询计划,您应该使用PROFILE来调查这一点。

 类似资料:
  • 黄金法则 二八原则 系统中 20% 的代码会消耗 80% 的性能!在进行性能优化时,我们应该始终坚持这个原则。 够用原则 如果有两种方式渲染图像,无法观察出哪个渲染的效果更好,那就选用性能消耗更低的方式。我们知道,RGBA4444 像素格式的 PNG 图像质量比 RGBA8888 像素格式的要低,但是如果在游戏效果上,无法观察出哪个效果好,我们应该坚持使用 RGBA4444 的像素格式,因为它占用

  • 对于我正在编写的游戏,我在非正方形地图上使用四叉树。四叉树用于查找给定最大半径(圆)内的相邻单位的冲突检测、要攻击的敌人、最近的基地等。 我想知道的是,如果将四边形树由矩形而不是正方形制成,是否存在性能问题?矩形地图不是将正方形地图划分为正方形,而是在四边形树中划分为大小相等的矩形。 矩形地图上的方形四叉树:将创建一个四叉树,填充整个地图,但左侧或底部有空白/未使用区域,具体取决于地图的方向(水平

  • 问题内容: 最近开始使用一个数据库,其中的约定是为每个表创建一个视图。如果您假设表和视图之间存在一对一的映射,那么我想知道是否有人可以告诉我这样做的性能影响。顺便说一句,这是在Oracle上。 问题答案: 假设问题是关于非具体化视图的,那么- 确实取决于该视图所基于的查询以及对其执行的操作。有时,谓词可以由优化器推入视图查询中。如果不是这样,那将不如表格本身好。视图建立在表格之上- 为什么您期望性

  • 问题内容: 我在JSF1.2和Richfaces 3.3.2中构建了一个树分页,因为我有很多树节点(大约80k),而且速度很慢。 因此,作为首次尝试,我将创建一个带有页面和页面节点列表的HashMap。 但是,性能还不够好… 所以我想知道是否是比HashMap更快的东西,也许是列表列表之类的东西。 有人对此有经验吗?我能做什么? 提前致谢。 编辑。 最大的问题是,我必须在树的子节点中验证用户的权限

  • 我对这个项目很感兴趣,想了解更多关于RedisGgraph内部的信息,并寻找Redis-Streams和Redis-Ggraph模块之间互操作性的可行性。 因此,我想知道您在Redis的哪些本地数据结构中构建了您自己的“图形数据”数据结构,当我们运行TYPE myGgraph命令时,该数据结构会显示出来。 是RedisGgraph模块(或其子组件、节点、边、路径)内部的图,是建立在Redis的已知

  • 图形与显示 [AGP] agp={off|try_unsupported} off 表示关闭内核的AGP(CONFIG_AGP)支持; try_unsupported 表示尝试驱动那些不受支持的芯片(可能会导致系统崩溃或数据错误) [HW,DRM] gamma=浮点数 设置显示器的Gamma值。 video.brightness_switch_enabled={0|1} [背景知识]如果ACPI