我有一个名为&area 39覆盖的字段'在MySQL数据库中,其中包含邮政编码的字符串列表。
有两行具有相似的数据,例如:
Row 1: 'B*,PO*,WA*'
Row 2: 'BB*, SO*, DE*'
注意 - 字符串没有任何特定顺序,可能会因用户而改变
现在,如果我要使用如下查询:
SELECT * FROM technicians WHERE areasCovered LIKE '%B*%'
我希望它返回JUST Row 1.但是,由于字符串中的BB *,它也会返回第2行。
我怎么能阻止它这样做?
答案 0 :(得分:4)
在这种情况下使用like
的关键是包含分隔符,因此您可以查找分隔值:
SELECT *
FROM technicians
WHERE concat(', ', areasCovered, ', ') LIKE '%, B*, %'
在MySQL中,您也可以使用find_in_set()
,但这个空间可能会导致您出现问题,因此您需要摆脱它:
SELECT *
FROM technicians
WHERE find_in_set('B', replace(areasCovered, ', ', ',') > 0
但是,最后,您不应将这些类型的列表存储为字符串。您应该将它们存储在一个单独的表,一个连接表中,每个技术人员和每个区域覆盖一行。这使得这些类型的查询更容易表达,并且它们具有更好的性能。
答案 1 :(得分:2)
答案 2 :(得分:1)
通常我讨厌REGEXP。但是哼哼:
SELECT * FROM technicians
WHERE concat(",",replace(areasCovered,", ",",")) regexp ',B{1}\\*';
解释一下:
摆脱讨厌的空间:
select replace("B*,PO*,WA*",", ",",");
在前面标记逗号
select concat(",",replace("B*,PO*,WA*",", ",","));
使用REGEX匹配"逗号B后跟一个星号":
select concat(",",replace("B*,PO*,WA*",", ",",")) regexp ',B{1}\\*';
答案 3 :(得分:0)
我无法在我的机器上检查它,但它应该可以工作:
SELECT * FROM technicians WHERE areasCovered <> replace(areaCovered,',B*','whatever')
如果'B *'不存在,则areasCovered将等于replace(areaCovered,',B *','whatever'),并且它将拒绝该行。 如果'B *'存在,则arecovered将不会被替换(areaCovered,',B *','whatever'),它将接受该行。
答案 4 :(得分:-1)
你可以像编程学生建议的那样去做
SELECT * FROM technicians WHERE areasCovered LIKE 'B*%'
或者您也可以使用查询限制
SELECT * FROM technicians WHERE areasCovered LIKE '%B*%' LIMIT 1
答案 5 :(得分:-1)
%B*%
在每一方都包含%,这使得它返回值包含B*
的所有行在文本的任何位置,但是您的要求是查找包含以{开头的值的值的所有行{1}}所以跟随查询应该做的工作。
B*