Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/315.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 如何使递归的多个关系与Django对称_Python_Django_Django Models_Many To Many_Django Orm - Fatal编程技术网

Python 如何使递归的多个关系与Django对称

Python 如何使递归的多个关系与Django对称,python,django,django-models,many-to-many,django-orm,Python,Django,Django Models,Many To Many,Django Orm,我也读过,但是下面的代码并不像Django文档描述的那样工作 #人物模型 从django.db导入模型 班级负责人(models.Model): name=models.CharField(最大长度=255) friends=models.ManyToManyField(“self”, 通过"友谊",, 通过_字段=('personA','personB'), 对称=正确, ) 定义(自我): 返回self.name 班级友谊(models.Model): personA=models.Fore

我也读过,但是下面的代码并不像Django文档描述的那样工作

#人物模型
从django.db导入模型
班级负责人(models.Model):
name=models.CharField(最大长度=255)
friends=models.ManyToManyField(“self”,
通过"友谊",,
通过_字段=('personA','personB'),
对称=正确,
)
定义(自我):
返回self.name
班级友谊(models.Model):
personA=models.ForeignKey(Person,on_delete=models.CASCADE,related_name='personA')
personB=models.ForeignKey(Person,on_delete=models.CASCADE,related_name='personB')
start=models.DateField(null=True,blank=True)
end=models.DateField(null=True,blank=True)
定义(自我):
返回'and'.join([str(self.personA),str(self.personB)])
如果
bill
ted
是朋友,我希望
bill.friends.all()
包括
ted
,而
ted.friends.all()
包括
bill
。事实并非如此
bill
的查询包括
ted
,但
ted
的查询不包括bill

>>> from people.models import Person, Friendship
>>> bill = Person(name='bill')
>>> bill.save()
>>> ted = Person(name='ted')
>>> ted.save()
>>> bill_and_ted = Friendship(personA=bill, personB=ted)
>>> bill_and_ted.save()
>>> bill.friends.all()
<QuerySet [<Person: ted>]>
>>> ted.friends.all()
<QuerySet []>
>>> ted.refresh_from_db()
>>> ted.friends.all()
<QuerySet []>
>>> ted = Person.objects.get(name='ted')
>>> ted.friends.all()
<QuerySet []>

>>来自people.models导入人物、友谊
>>>比尔=人(姓名=比尔)
>>>保存
>>>ted=个人(姓名='ted')
>>>ted.save()
>>>比尔和特德=友谊(personA=bill,personB=ted)
>>>比尔和特德保存()
>>>比尔,朋友们
>>>泰德,朋友们
>>>ted.refresh_from_db()
>>>泰德,朋友们
>>>ted=Person.objects.get(name='ted')
>>>泰德,朋友们
这是一个错误还是我误解了什么

编辑:更新代码,通过设置字段显示行为与
相同。

来源:

当中间模型上有多个外键指向参与多对多关系的任何(甚至两个)模型时,必须通过_字段指定
。这也适用于使用中介模型且模型有两个以上外键的情况,或者您希望显式指定应该使用哪两个Django


添加关系的正确方法是
bill.friends.add(ted)
。这将与
ted
交朋友
bill
ted
交朋友
bill
。如果要为中间模型上的额外字段设置值,在我的例子中是
开始
结束
,请使用
参数
添加()

在某些情况下,您希望
bill
->
ted
之间的关系在中间模型上的值与
ted
->
bill
不同。例如,当他们第一次见面时,
bill
认为
ted
很“酷”,但
ted
认为
bill
很“卑鄙”。在这种情况下,您需要helper函数

#人物模型
从django.db导入模型
班级负责人(models.Model):
name=models.CharField(最大长度=255)
friends=models.ManyToManyField(“自我”,通过class='friends')
定义(自我):
返回self.name
def add_友谊(self、person、impressionA、impressionB、recursive=True):
添加(person,通过默认设置={'personA\u impression':impressionA,'personB\u impression':impressionB)
如果是递归的:
添加友谊(自我、印象、印象、错误)
班级友谊(models.Model):
personA=models.ForeignKey(Person,on_delete=models.CASCADE,related_name='a')
personB=models.ForeignKey(Person,on_delete=models.CASCADE,related_name='b')
personA\u impression=models.CharField(最大长度=255)
personB_impression=models.CharField(最大长度=255)
定义(自我):
返回'and'.join([str(self.personA),str(self.personB)])
调用
bill.friends.add(ted,通过默认设置={“personA\u impression”:“cool”,“personB\u impression”:“mean”})
会产生以下结果:

...
>>> bill_and_ted = Friendship.objects.get(personA=bill)
>>> ted_and_bill = Friendship.objects.get(personA=ted)
>>> bill_and_ted.personA_impression
"cool"  # bill thinks ted is cool
>>> bill_and_ted.personB_impression
"mean"  # ted thinks bill is mean
>>> ted_and_bill.personA_impression
"cool"  # ted thinks bill is cool. This contradicts the bill_and_ted intermediate model

使用
add\u friendsy
函数为字段指定适当的值。

行为与
通过\u fields
设置的行为相同。我已更新了我的问题
...
>>> bill_and_ted = Friendship.objects.get(personA=bill)
>>> ted_and_bill = Friendship.objects.get(personA=ted)
>>> bill_and_ted.personA_impression
"cool"  # bill thinks ted is cool
>>> bill_and_ted.personB_impression
"mean"  # ted thinks bill is mean
>>> ted_and_bill.personA_impression
"cool"  # ted thinks bill is cool. This contradicts the bill_and_ted intermediate model