在Django中加入两个包含相同外键的表 [英] JOIN two tables containing same foreign key in Django

查看:478
本文介绍了在Django中加入两个包含相同外键的表的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

所以我有两个模型包含主键'User'

  class Reviews(models.Model):
subject_user = models.ForeignKey(User,related_name ='submitted_user')
actor = models.ForeignKey(User)## irrelavent
text = models.TextField()

class友谊(models.Model):
head_user = models.ForeignKey(User,related_name ='follow')
tail_user = models.ForeignKey(User)## irrelavent

现在我想查找也在 Friendsip.head_user 中的用户的所有评论。例如,说用户'1'用户'3'用户'5'

$ b $写了一个评论b

 评论:
subject_user_id actor_id文本
3 1 LoremIpsum1
5 1 LoremIpsum2

友谊:
head_user tail_user
3 9
8 9 ### Irrelavent

现在我输出应该是对应于'LoremIpsum1'的评论对象,即subject_user也存在于 Friendship.head_user 中的评论对象。我尝试了以下

  reviews = Reviews.objects.all()。select_related('friendship__head_user')

但它是给我所有的评论



编辑:



这是我如何插入评论:

  review,created = Reviews.object.get_or_create(subject_user = target,actor = actor)
review.text = NewReviewText
review.save()
/ pre>

解决方案

如果我正确理解你,这应该是有效的:

  heads =(f.head_user for f in Friendship.objects.all())
评论= Reviews.objects.all()。filter(subject_user__in= heads)

首先,您抓住友谊中的所有用户 s,然后找到所有的评论,这似乎符合您的要求:


我想查找所有的用户评论在友谊中。 head_user


你不能使用的原因 select_related 它是否希望在两种模式之间存在明确的关系,在这种情况下,这种模式不是。在评论友谊之间没有定义外键,所以在这种情况下最合适的方式可能是我已经提出了。



然而,直到你已经在愤怒中进行了测试,并做了一些分析来确认是系统中一个关键的慢点,我注意到Donald Knuth的话:


我们应该忘记小的效率,约97%的时间:过早优化是所有的根源



So I have two models containing primary key 'User'

class Reviews(models.Model):
    subject_user = models.ForeignKey(User,related_name='reviewed_user')
    actor = models.ForeignKey(User)                         ## irrelavent 
    text = models.TextField()

class Friendship(models.Model):
    head_user = models.ForeignKey(User,related_name='followed')
    tail_user = models.ForeignKey(User)                     ## irrelavent 

Now I want to find all the reviews of users who are also in the Friendsip.head_user. For example, say User '1' wrote a review each for User '3' and User '5'

Reviews:
subject_user_id     actor_id     text
3                   1            LoremIpsum1
5                   1            LoremIpsum2

Friendship:
head_user           tail_user
3                   9
8                   9      ### Irrelavent

Now I output should be reviews object corresponding to 'LoremIpsum1' i.e. the review object whose subject_user is also present in Friendship.head_user. I tried the following

reviews = Reviews.objects.all().select_related('friendship__head_user')

But it is giving me all the reviews

Edit:

This is how I insert the review:

review, created = Reviews.object.get_or_create(subject_user=target, actor=actor)
review.text = NewReviewText
review.save()

解决方案

If I understand you correctly, this should work:

heads = (f.head_user for f in Friendship.objects.all())
reviews = Reviews.objects.all().filter("subject_user__in"=heads)

First you grab all the head users in Friendships and then find all their reviews, which seems to match your requirement:

I want to find all the reviews of users who are also in the Friendship.head_user

The reason you can't use select_related is that it expects that there will be an explicit relationship between the two models, which in your case there is not. There is no foreign key defined between a Review and a Friendship, so in this case the most optimal way is probably what I've proposed.

However, until you've tested this in anger and done some analysis to confirm is is a critical slow point in your system, I'd heed the words of Donald Knuth:

We should forget about small efficiencies, say about 97% of the time: premature optimization is the root of all evil.

这篇关于在Django中加入两个包含相同外键的表的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆