You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何使用Django ORM去除查询结果中value字段值相同的重复记录

实现方案

完全可以通过Django ORM实现,也可以用兼容性更强的内存处理方案,两种方式都能满足你过滤连续重复value、仅保留值变化节点的需求,最终返回的数据量可以压缩到你预期的8000条左右。

方案1:数据库层实现(推荐,支持PostgreSQL/MySQL 8.0+/SQLite 3.25+)

利用窗口函数Lag获取同个指标(同机器、同name)的上一条记录的value,仅保留第一条或者value和上一条不同的记录即可。

代码修改

首先导入依赖:

from django.db.models import Window, F, Q
from django.db.models.functions import Lag

然后在你原有的查询过滤逻辑之后、分页之前,增加以下代码:

# 先按时间正序排序,保证相邻记录的时间顺序正确
queryset = queryset.order_by('date_time')
# 新增字段,存储同个机器同个指标的上一条记录的value
queryset = queryset.annotate(
    prev_value=Window(
        expression=Lag('value'),
        # 按机器、指标name分组,不同分组的记录互不影响
        partition_by=[F('machine_id'), F('name')],
        order_by=F('date_time').asc()
    )
)
# 仅保留第一条记录,或者value和上一条不同的记录
queryset = queryset.filter(Q(prev_value__isnull=True) | ~Q(prev_value=F('value')))

之后再走原有分页、序列化逻辑即可,返回的结果就是已经去重连续相同value的数据集。

方案2:应用层内存处理(全数据库兼容)

如果你的数据库版本不支持窗口函数,直接对查询结果做内存过滤即可,2.5万条数据的处理耗时仅为毫秒级,完全不会影响性能。

代码修改

在你原有查询过滤逻辑之后,替换原有分页、序列化逻辑为以下代码:

# 先按指标名称、时间排序
data_list = list(queryset.order_by('name', 'date_time'))
filtered_data = []
current_name = None
last_value = None

for item in data_list:
    # 遇到新的指标直接保留
    if item.name != current_name:
        filtered_data.append(item)
        current_name = item.name
        last_value = item.value
    # 同指标下value变化才保留
    else:
        if item.value != last_value:
            filtered_data.append(item)
            last_value = item.value

# 对过滤后的数据做分页和序列化
pagination = LargeResultsSetPagination()
paginated_qs = pagination.paginate_queryset(filtered_data, request)
serializer = TechnicalDataSerializer(paginated_qs, many=True)
return Response(serializer.data)

注意事项

  • 两种方案都是过滤连续重复的value,不会删除非连续的相同值记录,完全符合折线图的展示要求,不会丢失值变化的节点
  • 如果你的业务逻辑允许,优先选方案1,数据库层处理的性能更好,也支持原生分页
  • 如果指标和机器维度很多,内存处理的压力也不会明显上升,最多也就几万条数据,完全在Python的处理能力范围内

内容的提问来源于stack exchange,提问作者darkvodka

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.02 18:30:02