您现在的位置是:主页 > news > 河南做网站 河南网站建设/网红推广
河南做网站 河南网站建设/网红推广
admin2025/5/6 20:34:56【news】
简介河南做网站 河南网站建设,网红推广,网易企业邮箱手机怎么登录,做电商的批发网站有哪些关联的对象 当你在一个模型中定义一个关联关系时(例如,ForeignKey、 OneToOneField 或ManyToManyField),该模型的实例将带有一个方便的API 来访问关联的对象。 利用本页顶部的模型,一个Entry 对象e 可以通过blog 属性e…
关联的对象¶
当你在一个模型中定义一个关联关系时(例如,ForeignKey、 OneToOneField 或ManyToManyField),该模型的实例将带有一个方便的API 来访问关联的对象。
利用本页顶部的模型,一个Entry 对象e 可以通过blog 属性e.blog 获取关联的Blog 对象。
(在幕后,这个功能是通过Python 的描述器实现的。这应该不会对你有什么真正的影响,但是这里我们指出它以满足你的好奇)。
Django 还会创建API 用于访问关联关系的另一头 —— 从关联的模型访问定义关联关系的模型。例如,Blog 对象b 可以通过entry_set 属性 b.entry_set.all()访问与它关联的所有Entry 对象。
这一节中的所有示例都将使用本页顶部定义的Blog、 Author 和Entry 模型。
一对多关系¶
前向查询¶
如果一个模型具有ForeignKey,那么该模型的实例将可以通过属性访问关联的(外部)对象。
例如:
>>> e = Entry.objects.get(id=2)
>>> e.blog # Returns the related Blog object.
你可以通过外键属性获取和设置。和你预期的一样,对外键的修改不会保存到数据库中直至你调用save()。例如:
>>> e = Entry.objects.get(id=2)
>>> e.blog = some_blog
>>> e.save()
如果ForeignKey 字段有null=True 设置(即它允许NULL 值),你可以分配None 来删除对应的关联性。例如:
>>> e = Entry.objects.get(id=2)
>>> e.blog = None
>>> e.save() # "UPDATE blog_entry SET blog_id = NULL ...;"
一对多关联关系的前向访问在第一次访问关联的对象时被缓存。以后对同一个对象的外键的访问都使用缓存。例如:
>>> e = Entry.objects.get(id=2)
>>> print(e.blog) # Hits the database to retrieve the associated Blog.
>>> print(e.blog) # Doesn't hit the database; uses cached version.
注意select_related() 查询集方法递归地预填充所有的一对多关系到缓存中。例如:
>>> e = Entry.objects.select_related().get(id=2)
>>> print(e.blog) # Doesn't hit the database; uses cached version.
>>> print(e.blog) # Doesn't hit the database; uses cached version.
反向查询¶
如果模型I有一个ForeignKey,那么该ForeignKey 所指的模型II实例可以通过一个管理器返回前面有ForeignKey的模型I的所有实例。默认情况下,这个管理器的名字为foo_set,其中foo 是源模型的小写名称。该管理器返回的查询集可以用上一节提到的方式进行过滤和操作。
例如:
>>> b = Blog.objects.get(id=1)
>>> b.entry_set.all() # Returns all Entry objects related to Blog.# b.entry_set is a Manager that returns QuerySets.
>>> b.entry_set.filter(headline__contains='Lennon')
>>> b.entry_set.count()
你可以在ForeignKey 定义时设置related_name 参数来覆盖foo_set 的名称。例如,如果Entry 模型改成blog = ForeignKey(Blog, related_name='entries'),那么上面的示例代码应该改成这样:
>>> b = Blog.objects.get(id=1)
>>> b.entries.all() # Returns all Entry objects related to Blog.# b.entries is a Manager that returns QuerySets.
>>> b.entries.filter(headline__contains='Lennon')
>>> b.entries.count()
使用自定义的反向管理器¶
默认情况下,用于反向关联关系的RelatedManager 是该模型默认管理器 的子类。如果你想为一个查询指定一个不同的管理器,你可以使用下面的语法:
from django.db import modelsclass Entry(models.Model):#...objects = models.Manager() # Default Managerentries = EntryManager() # Custom Managerb = Blog.objects.get(id=1)
b.entry_set(manager='entries').all()
如果EntryManager 在它的get_queryset() 方法中使用默认的过滤,那么该过滤将适用于all() 调用。
当然,指定一个自定义的管理器还可以让你调用自定义的方法:
b.entry_set(manager='entries').is_published()
处理关联对象的其它方法¶
除了在上面”获取对象“一节中定义的查询集 方法之外,ForeignKey 管理器 还有其它方法用于处理关联的对象集合。下面是每个方法的大概,完整的细节可以在关联对象参考 中找到。
- add(obj1, obj2, ...)
- 添加一指定的模型对象到关联的对象集中。 create(**kwargs)
- 创建一个新的对象,将它保存并放在关联的对象集中。返回新创建的对象。 remove(obj1, obj2, ...)
- 从关联的对象集中删除指定的模型对象。 clear()
- 从关联的对象集中删除所有的对象。
若要一次性给关联的对象集赋值,只需要给它赋值一个可迭代的对象。这个可迭代的对象可以包含对象的实例,或者一个主键值的列表。例如:
b = Blog.objects.get(id=1)
b.entry_set = [e1, e2]
在这个例子中,e1 和e2 可以是Entry 实例,也可以是主键的整数值。
如果有clear() 方法,那么在将可迭代对象中的成员添加到集合中之前,将从entry_set 中删除所有已经存在的对象。如果没有clear() 方法,那么将直接添加可迭代对象中的成员而不会删除所有已存在的对象。
这一节中提到的每个”反向“操作都会立即对数据库产生作用。每个添加、创建和删除操作都会立即并自动保存到数据库中。
多对多关系¶
多对多关系的两端都会自动获得访问另一端的API。这些API 的工作方式与上面提到的“方向”一对多关系一样。
唯一的区别在于属性的名称:定义 ManyToManyField 的模型使用该字段的属性名称,而“反向”模型使用源模型的小写名称加上'_set' (和一对多关系一样)。
一个例子可以让它更好理解:
e = Entry.objects.get(id=3)
e.authors.all() # Returns all Author objects for this Entry.
e.authors.count()
e.authors.filter(name__contains='John')a = Author.objects.get(id=5)
a.entry_set.all() # Returns all Entry objects for this Author.
类似ForeignKey,ManyToManyField 可以指定related_name。在上面的例子中,如果Entry 中的ManyToManyField 指定related_name='entries',那么Author 实例将使用 entries 属性而不是entry_set。
一对一关系¶
一对一关系与多对一关系非常相似。如果你在模型中定义一个OneToOneField,该模型的实例将可以通过该模型的一个简单属性访问关联的模型。
例如:
class EntryDetail(models.Model):entry = models.OneToOneField(Entry)details = models.TextField()ed = EntryDetail.objects.get(id=2)
ed.entry # Returns the related Entry object.
在“反向”查询中有所不同。一对一关系中的关联模型同样具有一个管理器对象,但是该管理器表示一个单一的对象而不是对象的集合:
e = Entry.objects.get(id=2)
e.entrydetail # returns the related EntryDetail object
如果没有对象赋值给这个关联关系,Django 将引发一个DoesNotExist 异常。
实例可以赋值给反向的关联关系,方法和正向的关联关系一样:
e.entrydetail = ed