我在Django應用程序中有以下查詢。用戶字段是一個外鍵。結果可能包含1000個MyModel對象,但僅適用於少數用戶。我想限制它在查詢的user__in=
部分中爲每個用戶返回的5個MyModel對象。我應該以5 *#用戶或更少的MyModel對象結束。Django ORM限制queryset只返回數據的一個子集
lfs = MyModel.objects.filter(
user__in=[some,users,here,],
active=True,
follow=True,
)
通過ORM或SQL(使用Postgres)都是可以接受的。
感謝
EDIT 2
發現了一個簡單的方法來完成這件事,我已經添加了如下回答。
編輯
一些在評論中提到的鏈接有一些很好的信息,但沒有人真的在Postgres或者Django的ORM工作。對於其他人在未來尋找這些信息,我在這些其他問題/ asnwers的代碼的適應。
爲了實現這一點是Postgres的9.1,我不得不創建一個使用pgperl一對夫婦的功能(這也需要我安裝pgperl)
CREATE OR REPLACE FUNCTION set_int_var(name text, val bigint) RETURNS bigint AS $$
if ($_SHARED{$_[0]} = $_[1]) {
return $_[1];
} else {
return $_[1];
}
$$ LANGUAGE plperl;
CREATE OR REPLACE FUNCTION get_int_var(name text) RETURNS bigint AS $$
return $_SHARED{$_[0]};
$$ LANGUAGE plperl;
而我最終的查詢看起來像以下
SELECT x.id, x.ranking, x.active, x.follow, x.user_id
FROM (
SELECT tbl.id, tbl.active, tbl.follow, tbl.user_id,
CASE WHEN get_int_var('user_id') != tbl.user_id
THEN
set_int_var('rownum', 1)
ELSE
set_int_var('rownum', get_int_var('rownum') + 1)
END AS
ranking,
set_int_var('user_id', tbl.user_id)
FROM my_table AS tbl
WHERE tbl.active = TRUE AND tbl.follow=TRUE
ORDER BY tbl.user_id
) AS x
WHERE x.ranking <= 5
ORDER BY x.user_id
LIMIT 50
唯一的缺點是,如果我試圖通過使用user_id IN()來限制它尋找的用戶,那麼整個事情就會中斷,它只會返回每一行,而不是每個用戶5個。
的可能重複[Django的:如何選擇行有限數量的每一個外鍵(http://stackoverflow.com/questions/6705579/django-how-to-select-a-limited - 行數爲每個外鍵) – DrTyrsa 2012-03-01 08:00:18
它**是**重複。我查了一下,似乎是另一個問題的答案,尤其是代碼的第一部分,回答了這個問題。 – jpic 2012-03-01 09:38:31
順便說一句,這被稱爲前n個查詢。 – jpic 2012-03-01 10:42:13