use*_*778 1 django django-models
我有两张这样的表:
class Collection(models.Model):
name = models.CharField()
class Image(models.Model):
name = models.CharField()
image = models.ImageField()
collection = models.ForeignKey(Collection)
Run Code Online (Sandbox Code Playgroud)
我想从每个集合中检索第一张图像。我尝试过:
image_list = Image.objects.order_by('collection.id').distinct('collection.id')
Run Code Online (Sandbox Code Playgroud)
但它并没有像我预期的那样工作:(
有任何想法吗?谢谢。
不要使用点来分隔 Django 中跨越关系的字段;改为使用双下划线约定——它的意思是“按照这个关系到达这个领域”
这是更正确的:
image_list = Image.objects.order_by('collection__id').distinct('collection__id')
Run Code Online (Sandbox Code Playgroud)
但是,它可能不会执行您想要的操作。
“第一”的概念并不总是像您使用它的方式那样适用于关系数据库。对于图像表中具有相同集合 id 的所有记录,没有记录是“第一个”或“最后一个”——它们都只是记录。您可以在该表上放置另一个字段来定义特定顺序,或者您可以按 id 或按名称的字母顺序排序,但默认情况下这些都不会发生。
最适合您的是通过一个查询获取集合列表,然后在单独的查询中为每个集合获取一个项目:
collection_ids = Image.objects.values_list('collection', flat=True).distinct()
image_list = [
Image.objects.filter(collection__id=c)[0] for c in collection_ids
]
Run Code Online (Sandbox Code Playgroud)
如果要将订单应用于图像,以定义哪个是“第一个”,然后像这样修改它:
collection_ids = Image.objects.values_list('collection', flat=True).distinct()
image_list = [
Image.objects.filter(collection__id=c).order_by('-id')[0] for c in collection_ids
]
Run Code Online (Sandbox Code Playgroud)
您还可以编写原始 SQL —— MySQL 聚合有一个有趣的特性,即未聚合的字段仍然可以出现在最终输出中,并且基本上从匹配记录集中获取一个随机值。像这样的事情可能会奏效:
Image.objects.raw("SELECT image.* FROM app_image GROUP BY collection_id")
Run Code Online (Sandbox Code Playgroud)
此查询应该为您从每个集合中获取一张图像,但您无法控制返回哪个图像。
| 归档时间: |
|
| 查看次数: |
6526 次 |
| 最近记录: |