django如何在不进行太多查询的情况下检查此应用程序上是否已存在用户?

时间:2012-12-27 00:54:33

标签: django django-queryset

假设这些为django模型:

class Question():

    question = charfield()
    choice = charfield(choices = answer_choice)

class Answer():

    question = models.foreignkey(Question, related_name = 'answers')
    answerer = models.foreignkey('auth.User')
    answer = models.charfield()

我正在构建一个页面,其中我显示100个问题,每个User可以回答,但无法更改每个问题的答案。对于每个问题,我必须检查User上是否已存在Answerer。然后我制作模板标签:     @ register.filter     def this_user_exists(user,obj):         obj = obj.answers.filter(answerer_id = user.id)         return obj

然后在模板上:

# obj is list of question
{% if not user|this_user_exists:obj %}
    # can answer
{% else %}
    # cannot answer
{% endif %}

问题是,对于每个问题,它会生成1个查询,因此对于100个问题,它将生成100个查询。我尝试使用此查询来生成问题Question.objects.all()Question.objects.prefetch_related('answers'),但仍然遇到了问题。有没有更好的方法来实现这一目标而不会进行太多的查询?

2 个答案:

答案 0 :(得分:2)

要减少查询,您可以先查询所需的答案,然后获取所有相关的答案,

answers = Answer.objects.select_related('answerer').filter(xxxx)

# fetch related user id's
userids_in_answer = [answer.answerer.id for answer in answers]

# fetch user ids
user_id_set = set(User.objects.filter(id__in=userids_in_answer).values('id', flat=True)

之后,您可以通过

轻松了解用户是否存在
for answer in answers:
  if answer.answerer.id in user_id_set:
      xxx

减少了查询数量,您可以检查这是否有帮助。

答案 1 :(得分:0)

在您看来:

answered_ids = [ans.question_id for ans in Answer.objects.filter(answerer=request.user)]

在你的模板中:

{% if not obj.id in answered_ids %}
    # can answer
{% else %}
    # cannot answer
{% endif %}