ObjectDoesNotExist与.filter()。first()并检查无
问题描述:
在Django 1.6中,他们引入了.first()
以获取查询集的第一个元素。 [Source]ObjectDoesNotExist与.filter()。first()并检查无
现在有2种方式来获得一个元素:
user_id = 42
try:
obj = User.objects.get(id=user_id)
except ObjectDoesNotExist:
raise Exception("Invalid user id given")
和:
user_id = 42
obj = User.objects.filter(id=user_id).first()
if not obj:
raise Exception("Invalid user id given")
继Python的方式来请求原谅,第一个是比较欣赏的方式使用。 然而,第二个可能更容易理解,并且缩短了一行。
Q1:这两个代码片段的速度有什么不同吗?
Q2:哪一个是获取单个对象的首选方式?
答
这两者有不同的语义和不同的gaurantees。主要区别在于它们如何处理多个匹配对象。
.get()
如果多个对象与给定的查询匹配,则会引发异常。因此,您应该使用.get()
根据唯一属性(如id
)或一组属性获取项目。
.first()
将基于定义的顺序返回第一个项目,如果多个对象与给定查询匹配的话。当你需要一个单独的项目时,用它来过滤非唯一的属性,第一个项目基于一些(可能未定义的)顺序。
因此,虽然.get()
保证只有一个项目匹配查询,但.first()
只能保证它基于给定的顺序返回第一个项目。
他们如何处理丢失的对象更多的是语义的情况。将异常转换为None
或其他方法很简单。虽然你可能会在这里和那里保存一行,但我不会根据我的决定在这个上面使用一个。性能差异也可以忽略不计,并且可能取决于查询的结果。