django 1.8 queryset上的条件注释

时间:2015-10-23 21:06:55

标签: python sql django django-models

我有一个类似于以下内容的模型:

class MyStat(Model):
     metric = ForeignKey(MetricType) 
     source = ForeingKey(SourceType)

     total_units = IntegerField()
     metric_units = IntegerField()

     objects = MyQuerySet().as_manager()

查询在其代码

中执行以下操作
rollup = self.order_by().values(source.name)\.
                 annotate(mu=Sum('metric_units'), tu=Sum('total_units'))

这很有效。但是,我想修改一些依赖于所使用的metric类型的注释。不知何故,创建一个数据库端条件,将略有不同的注释(下面的伪代码):

if metric is some_metric:
      .annotate(mu=.8*Sum('metric_units'))
else:
      .annotate(mu=Sum('metric_units'))

显然上面的语法是无效的,但是我想知道是否有办法设置我的查询集来在数据库端做类似的事情

1 个答案:

答案 0 :(得分:1)

您可以使用Case进行条件表达。

让我们去注释部分。

免责声明:此代码未经测试

from django.db.models import Case, Value, When, FloatField, Sum

...annotate(mu=Case(When(metric=some_metric, then=Value(.8*Sum('metric_units')),
                    default=Value(Sum('metric_units')),
                    output_field=FloatField())))

如果需要匹配列表中的多个值,可以创建When个对象的列表:

whens = []
for some_metric in some_metrics:
    whens.append(When(metric=some_metric, then=Value(some-value-here)))

...annotate(mu=Case(*whens, default=Value(Sum('metric_units')),
                            output_field=FloatField()))