如何解决通过SQL语句基于另一个表的查询列表来进行INSERT的优雅方式?
我在MySQL 5.6数据库中有一个表persons
,如下所示:
persons
---------------------------------------------------
| id | name | sports |
---------------------------------------------------
| 1 | Adam | Football,Hockey |
| 2 | Ben | Hockey,Tennis |
| 3 | Charlie | Basketball |
| 4 | Dennis | Hockey,Baseball |
---------------------------------------------------
如您所见,列sports
是一个字符串,但包含一个列表。 sports
是字符串列表的原因是因为该表是根据我无法影响的自动化步骤创建的。
我想找到所有喜欢某种运动类型的人。用%LIKE%
在运动字符串列中搜索当然是无效的。
我想保持原样,但为了寻找高效喜欢某种运动类型的人,我想像这样填写新的M:N表persons_sports
:
persons_sports
---------------------------------------------------
| id | person_id | sports |
---------------------------------------------------
| 1 | 1 | Football |
| 2 | 1 | Hockey |
| 3 | 2 | Hockey |
| 4 | 2 | Tennis |
| 5 | 3 | Basketball |
| 6 | 4 | Hockey |
| 7 | 4 | Baseball |
---------------------------------------------------
当然,我可以编写一个脚本来获取persons
中的所有行,解析sports
列,然后填充新表,但是我想知道是否有一种不错且优雅的方法可以通过直接在数据库服务器上使用SQL语句?
解决方法
如果您有一个包含运动列表的表,则可以使用find_in_set()
进行此操作:
select p.person_id,s.sport
from persons p
inner join sports s on find_in_set(s.sport,p.sports)
如果不这样做,那就更复杂了。一种选择是使用递归cte(在MySQL 8.0中可用)迭代地拆分字符串:
with recursive
data as (select id,concat(sports,',') sports from persons),persons_sports as (
select
id,substring(sports,1,locate(',sports) - 1) sport,sports) + 1) rest
from data
union all
select
id,substring(rest,rest) - 1),rest) + 1)
from persons_sports
where locate(',rest) > 0
)
select id,sport from persons_sports
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。