我一直在寻找一些关于我如何选择数据库中的行的方法,其中一个数组将某些值与另一个表中的另一个数组相匹配。
我有一个名为" users"的表。在表格内部有一个名为" user_interests"包含一个有兴趣的数组。一个例子可能是"食物,时尚,音乐"作为一种价值。
在另一个名为" posts"包含一个名为" post_keywords"的列。使用另一个数组的值,例如" users"表
任何人都可以帮我找到选择符合用户兴趣的帖子的正确方法吗?到目前为止,我了解到我必须在MySQL查询中执行此操作。
提前致谢。
答案 0 :(得分:1)
在我们回答所提出的问题之前,我们应该解决一个更重要的重要的问题:我们是否应该真正将值存储在逗号分隔的列表中。这是一个SQL反模式。
&lt;! - 在Bill Karwin的优秀大部分第2章中解释了特定的SQL反模式: SQL反模式:避免数据库编程的陷阱,可从许多优秀的书商那里获得,包括亚马逊< / p>
https://www.amazon.com/SQL-Antipatterns-Programming-Pragmatic-Programmers/dp/1934356557
- &GT;
本章还讨论了一个更合适的SQL模式,将值存储为单独的行,每个值都在自己的行上。这就是SQL设计为在行上运行的方式。
在考虑警告之后,如果您仍然需要在字符串中以逗号分隔的值列表中搜索值...
MySQL提供 FIND_IN_SET
函数,该函数将返回列表中值的位置。
如果找到匹配值,该函数将返回一个正整数。
如果匹配的值 not ,则该函数将返回0.如果其中一个参数为NULL,则该函数将返回NULL。
作为函数如何工作的简单演示:
SELECT FIND_IN_SET('bowling' ,'food,fashion,music') -- > 0
, FIND_IN_SET('food' ,'food,fashion,music') -- > 1
, FIND_IN_SET('fashion' ,'food,fashion,music') -- > 2
, FIND_IN_SET('music' ,'food,fashion,music') -- > 3
为了在查询中使用它,MySQL允许我们在布尔上下文中使用表达式......
SELECT t.id
FROM my_table t
WHERE FIND_IN_SET('food' ,t.my_comma_separated_list_col)
AND FIND_IN_SET('music' ,t.my_comma_separated_list_col)
这将返回my_table
中具有my_comma_separated_list_col
值的行,例如:
'food,music'
'bowling,dancing,food,music'
'music,food'
如果在列表中找到指定的搜索值(例如'food'),FIND_IN_SET
将返回一个正整数,在布尔上下文中计算结果为TRUE。
如果在列表中找不到指定的值,FIND_IN_SET
将返回0,其值为FALSE。
返回NULL只是一个NULL,既不是TRUE也不是FALSE。
备注:强>
NULL值将导致FIND_IN_SET返回NULL。
SELECT FIND_IN_SET(NULL ,NULL) -- > NULL
, FIND_IN_SET(NULL ,'food,fashion,music') -- > NULL
, FIND_IN_SET('food',NULL) -- > NULL
列表中的值中的前导空格和尾随空格,或者找不到要搜索的值。除非搜索值和列表值都是精确匹配,包括前导和尾随空格。 (所以,不要在列表中的值之间使用任何空格):
值列表中的前导和/或尾随空格导致“未找到”
SELECT FIND_IN_SET('bowling' ,' food, fashion, music') -- > 0
, FIND_IN_SET('food' ,' food, fashion, music') -- > 0 !
, FIND_IN_SET('fashion' ,' food, fashion, music') -- > 0 !
, FIND_IN_SET('music' ,' food, fashion, music') -- > 0 !
;
SELECT FIND_IN_SET('bowling' ,'food ,fashion ,music ') -- > 0
, FIND_IN_SET('food' ,'food ,fashion ,music ') -- > 0 !
, FIND_IN_SET('fashion' ,'food ,fashion ,music ') -- > 0 !
, FIND_IN_SET('music' ,'food ,fashion ,music ') -- > 0 !
;
值中的前导或尾随空格会导致“找不到”
SELECT FIND_IN_SET('bowling' ,'food,fashion,music') -- > 0
, FIND_IN_SET('food ' ,'food,fashion,music') -- > 0 !
, FIND_IN_SET(' fashion' ,'food,fashion,music') -- > 0 !
, FIND_IN_SET(' music ' ,'food,fashion,music') -- > 0 !
;