简体   繁体   English

DBAL基数违规错误

[英]DBAL cardinality violation error

I am getting the 'Cardinality Violation' error, for the following SQL: 我收到以下SQL的“基数违规”错误:

Doctrine\\DBAL\\Exception\\DriverException: An exception occurred while executing Doctrine \\ DBAL \\ Exception \\ DriverException:执行时发生异常

SELECT p.* FROM mod_products_products p 
LEFT JOIN mod_products_products_categories c_link ON c_link.product_id = p.id 
LEFT JOIN mod_products_brands b ON p.brand_id = b.id 
LEFT JOIN mod_products_groups vg ON p.variation_id = vg.id 
LEFT JOIN mod_products_categories c ON c_link.category_id = c.id 
LEFT JOIN mod_products_group_options vg_o ON vg_o.group_id = vg.id 
LEFT JOIN mod_products_group_values vg_o_v ON vg_o_v.option_id = vg_o.id 
WHERE (p.name LIKE (?, ?)) AND (p.parent_id = 0) AND (vg_o.disabled=0) 
GROUP BY p.id ORDER BY p.name ASC 
LIMIT 18446744073709551615 OFFSET 0

with params ["%big%", "%light%"]: SQLSTATE[21000]: Cardinality violation: 1241 Operand should contain 1 column(s). with params [“%big%”,“%light%”]:SQLSTATE [21000]:基数违规:1241操作数应包含1列。

The error only occurs if there is more than one value defined in the parameter list for WHERE (p.name LIKE (?, ?)) . 只有在WHERE (p.name LIKE (?, ?))的参数列表中定义了多个值WHERE (p.name LIKE (?, ?))时才会出现该错误。

I am using executeQuery() , and passing the array as Connection::PARAM_STR_ARRAY . 我正在使用executeQuery() ,并将数组作为Connection::PARAM_STR_ARRAY In the original statement I am defining the trouble point as: 在原始声明中,我将故障点定义为:

$builder->andWhere('p.name LIKE (:partial_names)');

It seems it doesn't like getting an array passed as partial_names. 它似乎不喜欢将数组作为partial_names传递。 Any ideas on what is causing this, and how to avoid it? 关于导致这种情况的原因以及如何避免它的任何想法?

MySQL LIKE is a "string comparison function" and as such compares one string to another, using "simple pattern matching". MySQL LIKE是一个“字符串比较函数”,因此使用“简单模式匹配”将一个字符串与另一个字符串进行比较。

If you check the SQL standard , you'll notice that the BNF grammar for LIKE accepts only "character-like" and "octet-like" arguments, both of which are essentially what we'd call strings. 如果你检查SQL标准 ,你会注意到LIKEBNF语法只接受“类似字符”和“八位字节”的参数,这两个参数基本上都是我们称之为字符串的。 (There is some detail around the fact that LIKE performs a binary, character-for-character match on the RHS, which is different than how = operates: foo LIKE 'bar' and foo='bar' may produce different results.) (有一些细节围绕这样的事实: LIKE在RHS上执行二进制,字符对字符匹配,这与how =操作不同: foo LIKE 'bar'foo='bar'可能产生不同的结果。)

All this means you can't do LIKE ('a', 'b') because the columnar expression ('a', 'b') is not string-like. 所有这些意味着你不能LIKE ('a', 'b')因为柱状表达式('a', 'b')不是字符串式的。 Or in geeky standard language, it's cardinality (2) differs from the expected cardinality (1). 或者用令人讨厌的标准语言,它的基数(2)与预期的基数(1)不同。 However, you can do this in MySQL and SQLite (maybe other engines): 但是,您可以在MySQL和SQLite(可能是其他引擎)中执行此操作:

WHERE foo LIKE ('%bar')

because the cardinality of the RHS is 1 (there is one column), which is what LIKE expects. 因为RHS的基数是1(有一列),这是LIKE期望的。

You're wanting something effectively similar to foo LIKE IN ('a', 'b') , but that doesn't exist either (for the SQL standard reason mentioned above). 你想要的东西有效类似于foo LIKE IN ('a', 'b') ,但这也不存在(对于上面提到的SQL标准原因)。 This Q&A shows some workarounds for that behavior, REGEXP based being the accepted answer. 此问答显示了该行为的一些解决方法,基于REGEXP是接受的答案。

So, to get around this error, you need to rewrite your query to use multiple LIKE , or a REGEXP , or maybe even something like FIND_IN_SET . 因此,要解决此错误,您需要重写查询以使用多个LIKE ,或REGEXP ,甚至可能像FIND_IN_SET

Change 更改

(p.name LIKE (?, ?))

to

(p.name LIKE ? OR p.name LIKE ?)

and

["%big%", "%light%"]

to

"%big%", "%light%"

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 Symfony DBAL插入提供:“语法错误或访问冲突:1064” - Symfony DBAL insert gives: “Syntax error or access violation: 1064” 如何在php&mysql中纠正基数违反错误消息 - how to rectify cardinality violation error message in php&mysql PDO INSERT INTO SQLSTATE [21000]:基数违反:1241错误 - PDO INSERT INTO SQLSTATE[21000]: Cardinality violation: 1241 error 为什么我的查询导致基数违规错误PDO / PHP MySQL - Why my query causes in Cardinality violation error PDO/PHP MySQL 获取错误 - SQLSTATE [21000]:基数违规:1241操作数应包含1列 - getting error - SQLSTATE[21000]: Cardinality violation: 1241 Operand should contain 1 column(s) Doctrine \\ DBAL \\ Driver \\ PDOException::(“SQLSTATE [42000]:语法错误或访问冲突:1071指定密钥太长;最大密钥长度为767字节”) - Doctrine\DBAL\Driver\PDOException::(“SQLSTATE[42000]: Syntax error or access violation: 1071 Specified key was too long; max key length is 767 bytes”) 使用PDO在多次插入中违反基数 - Cardinality violation In Multi Insert Using PDO 从表中删除会导致基数违反 - Deleting from a table results in a Cardinality violation DBAL连接作为服务引发错误 - DBAL connection as service throws error Zend Framework基数违规:1241操作数应包含1列 - Zend Framework Cardinality violation: 1241 Operand should contain 1 column(s)
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM