gpt4 book ai didi

python - Django:每个外键返回一个过滤对象

转载 作者:太空宇宙 更新时间:2023-11-04 06:30:49 25 4
gpt4 key购买 nike

是否可以返回每个外键只返回一个对象的查询集?

例如,我想要从 django_comments 获取最新评论,但我只希望每个对象有一个评论(最新评论),即只返回对某个对象的最新评论并排除对该对象的所有过去评论.我想这类似于 django_comments.content_type 和 django_comments.object_pk 上的 sql group_by。

++添加信息++

最终目标是创建一个事件评论“线程”列表,根据线程具有最新评论显示/排序,就像您的标准讨论板,其主题按最近事件列出。

我认为最好的方法是抓取最新评论,然后按内容类型和 object_pk 对它们进行排序或分组,以便每个相关内容对象仅返回一个评论(最新)。然后我可以使用该评论来获取我需要的所有信息,所以线程这个词被宽松地使用,因为我真的只是捕获评论并跟随它的 pk's。

MODEL 是 django_threadedcomments,它扩展了 django_comments,为树、 child 和 parent 添加了一些字段。

查看:

...这将返回所有评论,包括父级的所有实例

comments = ThreadedComment.objects.all().exclude(is_public='0').order_by("-submit_date")

...这是理想的

comments = ThreadedComment.objects.all().exclude(is_public='0').order_by("submit_date").[plus sorting logic to exclude multiple instances of the same object_pk and content_type]

模板:

{% for comment in comments %}

TITLE: {{comment.content_object.title}}

STARTED BY : {{comment.content_object.user}}

MOST RECENT REPLY : {{comment.user}} on {{comment.submit_date}}

{% endfor %}

再次感谢!

最佳答案

这在 SQL 中是一件相当困难的事情;您可能无法通过 ORM 完成此操作。

您不能为此使用 GROUP BY。这用于告诉 SQL 如何对项目进行分组以进行聚合,这不是您在这里所做的。 "SELECT x, y FROM table GROUP BY x"是非法SQL,因为y的值没有意义。

让我们用一个清晰​​的模式来看这个:

CREATE TABLE objects ( id INTEGER PRIMARY KEY, name VARCHAR );
CREATE TABLE comments ( object_id INTEGER REFERENCES objects (id), text VARCHAR NOT NULL, date TIMESTAMP NOT NULL );

INSERT INTO objects (id, name) VALUES (1, 'object 1'), (2, 'object 2');
INSERT INTO comments (object_id, text, date) VALUES
(1, 'object 1 comment 1', '2010-01-02'),
(1, 'object 1 comment 2', '2010-01-05'),
(2, 'object 2 comment 1', '2010-01-08'),
(2, 'object 2 comment 2', '2010-01-09');

SELECT * FROM objects o JOIN comments c ON (o.id = c.object_id);

我见过的最优雅的方法是 Postgresql 8.4 的窗口函数。

SELECT * FROM (
SELECT
o.*, c.*,
rank() OVER (PARTITION BY object_id ORDER BY date DESC) AS r
FROM objects o JOIN comments c ON (o.id = c.object_id)
) AS s
WHERE r = 1;

这将按日期为每个对象选择第一个评论,最新的在前。如果您没有看到它在做什么,请自行执行内部 SELECT 并观察它如何生成 rank(),这使得它非常简单。

我知道使用 Postgresql 执行此操作的其他方法,但我不知道如何在其他数据库中执行此操作。

尝试动态地计算它可能会给您带来严重的麻烦——而且要使这些复杂的查询表现良好也需要更多的工作。您最好以简单的方式执行此操作:为每个对象存储一个 last_comment_id 字段,并在添加或删除评论时更新它,这样您就可以加入和排序。您或许可以使用 SQL 触发器来自动处理此更新。

关于python - Django:每个外键返回一个过滤对象,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3080326/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com