【发布时间】:2018-01-08 15:28:39
【问题描述】:
我有一些表在两个单独的 Django 模型中没有通过 FK 关系连接,我正在尝试做一个SubQuery。数据如下所示:
# "master" data table - reflects real property ownership by humans
# there are often changes to property ownership
class OwnershipRecord(Model):
parcel = CharField(max_length=10, unique=True)
owner_name = ...
other data fields ...
# Poor man's 'elastic search' or an index of sorts for OwnershipRecord
class Lead(Model):
ownership_record = OneToOneField(OwnershipRecord)
preforeclosure = BooleanField(default=False)
aggregated data/booleans/etc...
# "descriptor" table for a property
# there are not often changes to a property's physical traits
ResidentialMasterRecord(Model):
parcel = CharField(max_length=10, unique=True) # These are the SAME as OwnershipRecord
livablesqft = ...
lotsqft = ...
所以我正在研究一个可以按平方英尺过滤Lead 对象的查询。 Lead 与 OwnershipRecord 相关,但与 ResidentialMasterRecord 没有关系 - 它以“事实表”的形式存在,类似于特定地址的一组坐标。
我认为SubQuery 可以在这种情况下工作,我可以从OwnershipRecord 和ResidentialMasterRecord 中引用parcel 来实时链接两者。
这是非常慢。这是我正在尝试的查询:
from django.db.models import OuterRef, SubQuery
from myapp.models import OwnershipRecord, Lead, ResidentialMasterRecord
RMR_SQ = ResidentialMasterRecord.objects \
.filter(parcel=OuterRef("ownership_record__parcel"))
qs = Lead.objects.select_related('ownership_record') \
.annotate(sqft=SubQuery(RMR_SQ.values("livablesqft")[:1])) \
.filter(sqft__gte=1500)
我正在查看 15-45 分钟范围内的查询时间 - 但我最终会得到结果... 关于如何在保持非外键链接结构的同时加快这件事的任何想法?
Django 1.11.8 PostgreSQL 9.5 Droplet 带 8GB RAM,4 核
【问题讨论】:
-
我们在这里讨论了多少条记录?最好用于每个表/模型。您还可以包括每个模型中的所有字段吗?它可能有助于画出更好的画面(无论如何对我来说)。
-
外键列是否被索引?如果您有权访问 Postgresql 日志,您能否提取正在执行的完整查询,使用
EXPLAIN (ANALYZE, BUFFERS, VERBOSE) your_query运行它并将其粘贴到 explain.depesz.com 以轻松查看减速可能来自何处。 -
FK 列应始终被索引,否则您将获得全表扫描而不是索引扫描。在小表上这很好,但在你的情况下,如果它们还没有被索引,你会看到一些好处。注意,FK 列默认不会在子端索引,但父端会有索引(由主键或唯一约束自动创建)。
-
@PANDAStack 没关系。我重新阅读它,我现在看到了重要的部分。我想保持“绝对数据量”选项处于打开状态,但这显然不是正在发生的事情。 bma 关于索引 FK 列的建议很可能是正确的路径。
-
另外,您也可以在其他列上添加索引。通常,当有人询问慢速数据库查询时,我的第一个问题是“您是否在表上构建了任何索引?”答案通常是否定的,或者我不知道。
标签: django postgresql