【问题标题】:Django queryset select where concatDjango queryset select where concat
【发布时间】:2016-12-21 10:07:50
【问题描述】:

我有一个这样的 sql 查询:

select *
from sys_user_promotion_record
where user_id=102 and concat(',' ,vendor_id, ',') like '%,1,%'

我怎样才能将该查询放入 django 查询集? 到目前为止,我设法制作了这个 django 查询集:

SysUserPromotionRecord.objects.filter(user_id=102, vendor_id__contains=','+'1'+',')

我怎样才能将concat(',' ,vendor_id, ',') 变成 django 查询集? 我避免在我的代码上使用原始 sql 查询。谢谢。

这是 vendor_id 值示例:

  • 1,11,14

  • 2,1,5

  • 3,5,11

sql执行时,会出现第1行和第2行。

【问题讨论】:

  • 你到底为什么要这样做? ` concat(',' ,vendor_id, ',') like '%,1,%'`
  • @e4c5 这有点难以解释。这个想法是将 1 与 11 或 12 或 13 等区分开来,所以我将 3,5,11 变为 ,3,5,11,所以当我查询 vendor_id like '%,1,%', vendor_id 3,5 时, 11 不会出现。
  • 那么为什么不能只查询 1?你知道 1 和 11 是不同的 :)
  • @e4c5 例如??你能给我更简单的查询吗?我的 vendor_id 是一个字符串
  • 你现在的问题实际上是“不清楚你在问什么”和“非 MVCE”类型闭包的好候选。你需要更好地解释你的问题。给你模型。例如

标签: mysql django select django-queryset concat


【解决方案1】:

您所做的应该可以工作,但我会假设 vendor_id 是一个整数,因此没有任何逗号。如果这是真的,您的查询将始终返回一个空查询集。

如果要查询 vendor_id IN (vendor_id1, vendor_id12, ...) 那么查询是.filter(vendor_id__in=list_of_vendor_ids)

但是,如果您的供应商 ID 确实是一个字符串并且可以包含逗号,那么您的查询应该可以工作,但您也需要处理边缘情况,例如“...,11”、“11”和“11”。 ...'。因此我建议这样的事情

from django.db.models import Q
vendor_query = Q(vendor_id__iregex=r'^{0},|,{0},|,{0}$|^{0}$'.format(vendor_id))
SysUserPromotionRecord.objects.filter(vendor_query, user_id=102)

编辑:看到您的更改,答案的第一部分似乎可以忽略。

编辑:将正则表达式更新为前一个 r',?{},?' 在搜索 1 时返回 11 等情况会返回错误结果

【讨论】:

  • 我不太了解这部分:Q(vendor_id__iregex=r',?{},?'.format(vendor_id))。我想从哪里得到vendor_id
  • 对不起。 vendor_id 在你的情况下是 11 所以你的正则表达式可以是 r',?11,?' 我把它作为一个变量认为 11 只是一个例子,你可以有不同的值
  • 正则表达式基本上会匹配 0 或 1 个逗号后跟 11 后跟 0 或 1 个逗号
  • 我在 django 中尝试过这段代码,但它显示的行数与 mysql 查询控制台不同。
  • 您的 MySQL 查询只选择那些具有 ,11, 的行。它会漏掉所有以 11 开头、以 11 结尾或只有 11 的人。例如 3,5,11
【解决方案2】:

like '%,1,%' 类型的 mysql 查询是数据库杀手。

B 树索引可用于表达式中的列比较 使用 =、>、>=、

这里的根本问题是您没有标准化您的数据库。您不应该像这样存储数据的原因在这里得到了很好的解释:Is storing a delimited list in a database column really that bad? 您的首要任务是规范化您的数据库。

作为一个临时补丁,请查看 django Concat 函数。

http://dev.mysql.com/doc/refman/5.7/en/index-btree-hash.html

【讨论】:

  • 感谢您的建议。我现在意识到这个数据库结构很糟糕。我不是制作分贝的人。但是,稍后我将与他协商。谢谢
猜你喜欢
  • 2021-12-04
  • 2018-01-02
  • 2011-11-29
  • 1970-01-01
  • 2011-08-18
  • 2018-03-17
  • 1970-01-01
  • 2018-06-11
  • 1970-01-01
相关资源
最近更新 更多