逗号分隔值 sql

Posted

技术标签:

【中文标题】逗号分隔值 sql【英文标题】:Comma delimited values sql 【发布时间】:2014-04-29 01:19:49 【问题描述】:

从我的在线研究中,我发现了这个问题的两个答案,我试图远离它们。

    我无法修改表格或添加新表格,因为该软件是第三方软件,需要表格保持不变。

    我试图避免使用临时表或额外的用户定义函数。

这是我的问题。

数据库中有一个列是用逗号分隔的数字列表,表示星期几,即 (1,2,4,5,7)。

我正在尝试找到一种方法来读取该数据并找出该列是否代表连续 3 天的任何行。

它应该返回任何带有

的东西
1,2,3  
2,3,4  
3,4,5  
5,6,7  
1,,,,,6,7  
1,2,,,,,7  

但是如果列有 1,2,3,4 它不应该返回两次。有很多行有 2,3,4,5,6,我想出的任何解决方案都会返回 3 次。

最好我想创建一个存储过程来传递一个数字并查找该连续天数。所以如果传入 5,它会查找连续 5 天被标记的任何东西。

除了使用额外的表格之外,还有其他选择吗?如果是这样,你能告诉我如何做这项工作吗?我对 SQL 并不陌生,但有很多我不熟悉的更高级的查询技术。

【问题讨论】:

一个选项是创建一个额外的表并规范化那里的数据。您可以保持原始表不变,但对此类查询使用规范化表。 您使用的是什么数据库? (请用数据库标记问题。)数字总是按顺序排列的吗? 我知道它是 sql2008,但不确定是否是 r2。我很想规范化数据库,但同样,它是一个正在读取数据的第三方应用程序,我无法控制源代码或表本身。 ... 如果您无法控制源或表本身,您的存储过程将如何被调用?如果您可以编写一个存储过程(并让它被调用),那么是什么阻止您创建其他可以让您解决这个问题的数据库对象? 我可以创建一个存储过程,我们正在使用报表中的表中的信息。我就是无法修改表格。 【参考方案1】:

以下暴力破解方法适用于所有数据库:

select (case when col like '%1%' and col like '%2%' and col like '%3%' then 1
             when col like '%2%' and col like '%3%' and col like '%4%' then 1
             when col like '%3%' and col like '%4%' and col like '%5%' then 1
             when col like '%4%' and col like '%5%' and col like '%6%' then 1
             when col like '%5%' and col like '%6%' and col like '%7%' then 1
             when col like '%6%' and col like '%7%' and col like '%1%' then 1
             when col like '%7%' and col like '%1%' and col like '%2%' then 1
             else 0
        end) as HasThreeConsecutiveDays

如果连续三天返回 0/1 标志。

【讨论】:

【参考方案2】:

所以如果传入5,它会查找连续5天被标记的任何东西。

如果没有动态 sql,您将无法做到这一点,因为您希望支持从 7 回绕到 1。如果您不关心,我可以编写一个查询,它会在单个语句中为您完成从一周结束回到开始,但是有了这个要求,如果不在过程中构建动态 sql 字符串,我不知道该怎么做,我现在没有时间玩(也许有人else 会接受这个想法并按照它运行)。

现在这个选项被打败了,我可以这样做:

WHERE
    (     col like '1,2,3%' 
       OR col like '%2,3,4%'
       OR col like '%3,4,5%'
       OR col like '%4,5,6%'
       OR col like '%5,6,7'
       OR col like '1%6,7'
       OR col like '1,2%7'
    )

这应该比检查另一个答案中显示的单个数字更好,因为要完成的模式匹配更少。但是,只有在我们可以保证排序顺序的情况下才有效。我们还需要提前知道数字之间的逗号是如何间隔的,但如果有必要,我们可以通过将所有逗号和/或空格替换为空字符串(并相应地调整模式)来解决这个问题。

这里还有一个想法:我意识到我可以支持天数参数,如果你可以设法在某个地方偷偷地在数据库中添加一个表。该表看起来像这样:

 create Table DayPatterns (Days int, Pattern varchar(13) ) 

表格中的数据如下所示:

1 1% 1 %2% 1 %3% ... 2 1,2% 2 %2,3% 2 %3,4% 2 %4.5% ... 2 1%7 ... 3 1,2,3% 3 %2,3,4% ... 3 1%6,7 3 1,2%7 ... 7 1,2,3,4,5,6,7

希望您了解如何填写。有了该表,您可以使用如下查询对表进行 JOIN:

INNER JOIN DayPatterns p ON p.Days = @ConsecutiveDays AND col LIKE p.Pattern

使这项工作(除了需要能够在某处创建该表)的关键还在于对正确的列执行 GROUP BY。否则,您最终会遇到与现在相同的问题,匹配多个可能的连续日模式将重复您的结果。

最后,您当然知道大多数包含 csv 数据的架构都已损坏,但由于您似乎无法修复此问题,希望这些想法之一会有所帮助。

【讨论】:

数据总是按数字顺序排列的,所以我明天试试这个并玩一下。我会告诉你我的最终解决方案。

以上是关于逗号分隔值 sql的主要内容,如果未能解决你的问题,请参考以下文章

在 Oracle SQL 中求和逗号分隔值

逗号分隔值 sql

如何在 Azure Databricks SQL 中将字段值转换为逗号分隔

SQL 从 XML 中获取列的逗号分隔值

Microsoft Access SQL 逗号分隔值

用逗号分隔的 Oracle sql 透视值