2016-11-13 34 views
4

在Django中,您創建的模型,可以選擇指定的字段的外鍵Do Django後退關係會增加開銷嗎?

class Man: 
     ... 

class Dog: 
     ... 
     owner = models.ForeignKey(Man, on_delete=models.SET_NULL) 

然後,您可以查詢每個Dog其各自所有者或得到所有的狗爲Man

owner = some_dog.owner 

all_dogs = some_man.dog_set.all() 

如果你不想創建the docs指定的後向關係,你可以做

class Man: 
     ... 

class Dog: 
     ... 
     owner = models.ForeignKey(Man, on_delete=models.SET_NULL, related_name='+') 

現在您無法訪問all_dogs = some_man.dog_set.all()

但是,這個額外的「建設」的後向關係會增加開銷嗎?
如果我只是從來沒有使用過all_dogs = some_man.dog_set.all()它是否會影響
我在Dog中指定了related_name='+'?它會減慢潛在的事情嗎?

而且這個功能是純粹在應用端Django中實現的,還是related_name='+'也會改變數據庫模式本身?

回答

4

但是,這個額外的「建設」的後向關係會增加開銷嗎?

沒有

如果我從來沒有使用過all_dogs = some_man.dog_set.all()會的問題我是否曾在狗指定related_name = '+'?它會減慢潛在的事情嗎?

不,沒有。

而且這個功能是純粹在應用端Django中實現的,還是將related_name ='+'也改變了數據庫模式本身?

它使用Python descriptors實現。在ForeignKey的情況下,這是ReverseManyToOneDescriptor。 數據庫模式沒有變化,並且存在或不存在相關名稱不會生成遷移。

如果您尚未禁用關係,則應該在模型類中實際看到描述符對象作爲屬性。類似這樣的:

>>> Dog.owner 
<django.db.models.fields.related_descriptors.ForwardManyToOneDescriptor at 0x105db25d0> 
>>> Man.dog_set 
<django.db.models.fields.related_descriptors.ReverseManyToOneDescriptor at 0x105db27d0> 

這些是使Django的ORM魔術工作的對象。