我有以下字段的用户模型..
class User(models.Model):
user_id = models.CharField(max_length=40,unique=True)
user_name = models.CharField(max_length=40)
user_email = models.EmailField()
user_city = models.CharField(max_length=40)
class Meta:
ordering = ['user_id']
verbose_name = 'User MetaData'
verbose_name_plural = 'Users MetaData'
def __unicode__(self):
return self.user_id
现在我想按用户筛选前10个城市,即该城市中拥有多个用户数的前10个城市的列表。我使用下面的语法但总是得到city_count = 1 ..
User.objects.annotate(city_count=models.Count('user_city')) .order_by('-city_count'))[:10]
我也尝试了以下语法但结果相同...
User.objects.values('user_city').annotate(city_count=models.Count('user_id')) .order_by('-city_count'))[:10]
我做错了什么?
答案 0 :(得分:2)
如果没有与User
有关系的模型,我认为你不能这样做。基本上,您需要在另一个模型上运行查询,然后从该其他模型注释user_city。对于你的具体情况,这有点奇怪。
但是,您可以在Python中执行此操作。我就是这样做的:
from collections import Counter
city_counter = Counter(User.objects.values_list('user_city', flat=True))
top_ten_cities_and_counts = city_counter.most_common()[:10]
top_ten_cities = [city for city, count in top_ten_cities_and_counts]
答案 1 :(得分:1)
你的第二个例子是对的,只是修复错别字。取代
User.objects.values('user_city').annotate(city_count=models.Count('user_id')) .order_by('-city_count'))[:10]
与
User.objects.values('user_city').annotate(city_count=models.Count('user_city')).order_by('-city_count')[:10]
更新1,2:
top_cities_queryset = (User.objects
.values('user_city')
.annotate(user_city_count=models.Count('user_city'))
.order_by('-user_city_count')
.values_list('user_city', 'user_city_count'))
top_cities = [{city: count} for city, count in top_cities_queryset]