MySQL逗号分隔字符串

MySQL逗号分隔字符串,mysql,Mysql,我的数据库中有一个状态字段,该字段的值为 172:6,173:6,174:7 其中1721774是我的id,6,7是我的状态,在我的字符串中用:分隔 现在我想在mysql中写一个查询来获取状态为6的id,如何分解字符串来获取id 我的第一个表是带有字段的education details表 id lead_ref status 1 R-1 172:6,173:6,174:7 我的下一个教育目标 id target_course name 172 A

我的数据库中有一个状态字段,该字段的值为

172:6,173:6,174:7
其中1721774是我的id,6,7是我的状态,在我的字符串中用:分隔

现在我想在mysql中写一个查询来获取状态为6的id,如何分解字符串来获取id

我的第一个表是带有字段的education details表

id   lead_ref  status
1      R-1      172:6,173:6,174:7 
我的下一个教育目标

id    target_course name
172      A
173      B
174      C
现在我想加入这两个表并获取状态为6的ID

SELECT `status`
FROM `table`
WHERE `status` LIKE `%:6,%`  -- if there is a matching status before a comma
   OR `status` LIKE `%:6`;   -- if there is matching status as last item

MySQL中不容易拆分/分解字符串。请参见

这是可能的,但这种方法更能说服您重新设计数据库,而不是将其用于实时环境中

通过将常量合并在一起,可以生成一系列数字。如果您将数字0到9并集并交叉连接,则可以生成数字0到99,并生成另一个交叉连接,以获得0到999,等等。您可以将此与子字符串_索引一起使用,以基于逗号拆分字符串

由于这将使用子字符串提供重复项,因此,通过这种方式,索引将使最后一个返回的次数与将返回的数量增加到它能处理的最大数量所需的次数相同,然后可以使用DISTINCT

SELECT DISTINCT SUBSTRING_INDEX(SUBSTRING_INDEX(SUBSTRING_INDEX(some_field, ',', 1 + units.i + tens.i * 10), ',', -1), ':', 1) AS id
FROM some_table
CROSS JOIN (SELECT 0 i UNION SELECT 1 UNION SELECT 2 UNION SELECT 3 UNION SELECT 4 UNION SELECT 5 UNION SELECT 6 UNION SELECT 7 UNION SELECT 8 UNION SELECT 9) units
CROSS JOIN (SELECT 0 i UNION SELECT 1 UNION SELECT 2 UNION SELECT 3 UNION SELECT 4 UNION SELECT 5 UNION SELECT 6 UNION SELECT 7 UNION SELECT 8 UNION SELECT 9) tens
WHERE SUBSTRING_INDEX(SUBSTRING_INDEX(SUBSTRING_INDEX(some_field, ',', 1 + units.i + tens.i * 10), ',', -1), ':', -1)  = 6
如果希望重复项返回正确的次数,则需要检查逗号分隔值的数量,将字段长度与字段长度进行比较,并将所有逗号替换为零,以获得逗号的数量:-

SELECT SUBSTRING_INDEX(SUBSTRING_INDEX(SUBSTRING_INDEX(some_field, ',', 1 + units.i + tens.i * 10), ',', -1), ':', 1) AS id
FROM some_table
CROSS JOIN (SELECT 0 i UNION SELECT 1 UNION SELECT 2 UNION SELECT 3 UNION SELECT 4 UNION SELECT 5 UNION SELECT 6 UNION SELECT 7 UNION SELECT 8 UNION SELECT 9) units
CROSS JOIN (SELECT 0 i UNION SELECT 1 UNION SELECT 2 UNION SELECT 3 UNION SELECT 4 UNION SELECT 5 UNION SELECT 6 UNION SELECT 7 UNION SELECT 8 UNION SELECT 9) tens
WHERE SUBSTRING_INDEX(SUBSTRING_INDEX(SUBSTRING_INDEX(some_field, ',', 1 + units.i + tens.i * 10), ',', -1), ':', -1)  = 6
AND (units.i + tens.i * 10) <= (LENGTH(some_field) - LENGTH(REPLACE(some_field, ',','')))
请注意,这两种方法最多只能处理100个逗号分隔的值。扩展它们以处理更多问题很容易,但这也会减慢查询速度

编辑-要获取状态的目标课程名称以及您现在在上面发布的演示日期,请执行以下操作:-

SELECT education_details.id, education.target_course_name
FROM education_details
CROSS JOIN (SELECT 0 i UNION SELECT 1 UNION SELECT 2 UNION SELECT 3 UNION SELECT 4 UNION SELECT 5 UNION SELECT 6 UNION SELECT 7 UNION SELECT 8 UNION SELECT 9) units
CROSS JOIN (SELECT 0 i UNION SELECT 1 UNION SELECT 2 UNION SELECT 3 UNION SELECT 4 UNION SELECT 5 UNION SELECT 6 UNION SELECT 7 UNION SELECT 8 UNION SELECT 9) tens
INNER JOIN education ON SUBSTRING_INDEX(SUBSTRING_INDEX(SUBSTRING_INDEX(status, ',', 1 + units.i + tens.i * 10), ',', -1), ':', 1) = education.id
WHERE SUBSTRING_INDEX(SUBSTRING_INDEX(SUBSTRING_INDEX(status, ',', 1 + units.i + tens.i * 10), ',', -1), ':', -1)  = 6
AND (units.i + tens.i * 10) <= (LENGTH(status) - LENGTH(REPLACE(status, ',','')));
SQL fiddle用于此:-


假设您希望172和173作为上述示例中的结果:我将解析出字符串,将其全部放入带有ID和STATUS列的临时表中,然后对其运行查询。如果有机会规范化数据库,您应该这样做。使用字符串比较和占位符进行选择是从DBMS检索数据的最坏情况。为关系创建一个单独的表并查询该表。我有许多表的联接,我只希望我的id状态应该是6,方法是将我的数据库规范化为临时表,然后使用有点复杂的过程。不,您现在正在做的是一项复杂的任务,当处理表中数百万个条目时,它将运行得非常慢。走对了路,这不是一个简单的问题——这将在将来为您节省很多麻烦……为此,我必须更改数据库结构,我没有时间做这么多更改。这样做的任何方法都可以处理到我的项目的下一阶段。如果您的条目中确实有逗号分隔的列表,而不是单独的列表,那么您应该使用我的答案版本条目。