如何解决分页性能
问题
给定以下查询:
MATCH (t:Tenant)-[:lives_in]->(:Apartment)-[:is_in]->(:City {name: 'City1'})
RETURN t
ORDER BY t.id
LIMIT 10
所以:“给我住在 City1 的前 10 个租户”
使用下面的示例数据,该数据库将针对 City1 中的每套公寓以及居住在这些公寓中的每个租户的每个租户而受到命中。
如果我删除 ORDER BY
这不会发生。
我正在尝试实现分页,所以我需要 ORDER BY
。如何提高这方面的表现?
示例数据
UNWIND range(1,5) as CityIndex
CREATE (c:City { id: CityIndex,name: 'City' + CityIndex})
WITH c,CityIndex
UNWIND range(1,5000) as ApartmentIndex
CREATE (a:Apartment { id: CityIndex * 1000 + ApartmentIndex,name: 'Apartment'+CityIndex+'_'+ApartmentIndex})
CREATE (a)-[:is_in]->(c)
WITH c,a,CityIndex,ApartmentIndex
UNWIND range(1,3) as TenantIndex
CREATE (t:Tenant { id: (CityIndex * 1000 + ApartmentIndex) * 10 + TenantIndex,name: 'Tenant'+CityIndex+'_'+ApartmentIndex+'_'+TenantIndex})
CREATE (t)-[:lives_in]->(a)
解决方法
如果没有 ORDER BY,cypher 可以懒惰地评估租户并在 10 处停止,而不是匹配 City1 中的每个租户。但是,因为您需要对租户进行排序,所以它唯一能做的就是获取所有租户然后进行排序。
如果可以住在公寓中的唯一标签是租户,那么您可以通过删除查询中的 Tenant
来保存过滤步骤,例如 MATCH (t)-[:lives_in]->(:Apartment)...
。
您可能还想检查查询的配置文件,看看它是否使用了 index backed order by
您希望从这个查询返回什么样的数字?给定城市中最坏的租户数量是多少?
编辑
我希望在 t 上使用 USING JOIN 会使用索引来改进计划,但事实并非如此。 如果您添加从租户到城市的冗余关系,查询的性能会稍好一些:
MATCH (t:Tenant)-[:CITY]->(:City {name: 'City1'})
RETURN t
ORDER BY t.id
LIMIT 10
类似地,通过将城市名称嵌入到租户中 - 没有重大收益。我对 City1 的 150,000 名租户进行了测试,也许当您接近数百万时,收益会更加明显,但不确定。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。