【问题标题】:Mysql where 1= 0 confusionmysql where 1=0 混淆
【发布时间】:2011-05-26 22:20:08
【问题描述】:

在简单的 sql 书中,有部分代码提到如果我使用 where 1 = 0,我可以安全地添加 OR 条件,例如:

WHERE
   1=0
   OR name LIKE '%Toledo%'
   OR billaddr LIKE '%Toledo%'
   OR shipaddr LIKE '%Toledo%'

我不明白为什么当我使用 where 1 = 0 时我可以安全地添加 OR 语句

我可以使用下面的东西吗?

WHERE
   1=1
   OR name LIKE '%Toledo%'
   OR billaddr LIKE '%Toledo%'
   OR shipaddr LIKE '%Toledo%'

我了解where 1=1 是添加 And 语句的快捷方式。
我明白因为where 1 =1 会返回true。我也可以将它用于Or 语句吗?
仍然没有得到零件where 1 = 0
任何解释都会很棒。

【问题讨论】:

  • 请注意,为了便于阅读,您也可以只使用where false or & where true and

标签: mysql select


【解决方案1】:

这取决于您正在处理的布尔运算的类型。如果要添加可变数量的AND 语句,则使用始终评估为真的语句,例如1 = 1。另一方面,如果你想对OR 语句做同样的事情,那么你应该使用一个评估为假的语句,例如1 = 0

假设您有一个布尔变量x,其真值不确定(可能为真,也可能为假。您不知道。)现在,如果您找到x AND false 的值,您获取false,不管x 的值是多少。

另一方面,如果你查看x OR true,你会得到true。同样,这与x 的真值无关。

在您的语句中,您希望硬编码的值对查询的逻辑没有影响。由于false OR a OR b OR c 在逻辑上等价于a OR b OR c,所以硬编码语句没有任何作用。在另一种情况下,true AND a AND b AND c 等价于a AND b AND c

【讨论】:

    【解决方案2】:

    MySQL 使用short-circuit boolean evaluation.

    一旦结果确定为 TRUE 或 FALSE,MySQL 就会停止评估其余行。

    TRUE OR ? OR ? 将始终为 TRUE,因此 MySQL 只会查看第一项而不测试其他任何内容。
    FALSE AND ? AND ? 将始终为 FALSE,因此 MySQL 不会再查看其他测试。

    这有一个(意想不到的)副作用,即 MySQL 永远不会使用 LIKE 查看您的表,而是返回以下查询中的所有行:

    SELECT * FROM atable
    WHERE
       1=1                         /* <--- this makes the whole OR set always true*/
       OR name LIKE '%Toledo%'     /* therefore the like tests are never done     */
       OR billaddr LIKE '%Toledo%' /*and all rows are returned */
       OR shipaddr LIKE '%Toledo%'
    

    在这个查询中:

    SELECT * FROM atable
    WHERE
       1=0                          /* false OR ? has an unknown outcome so */
       OR name LIKE '%Toledo%'      /* MySQL has to evaluate the LIKE tests */
       OR billaddr LIKE '%Toledo%'  /*only some rows will be returned*/
       OR shipaddr LIKE '%Toledo%'
    

    这与AND完全相反

    【讨论】:

      【解决方案3】:

      我可以使用下面的东西吗?

      WHERE
         1=1
         OR name LIKE '%Toledo%'
         OR billaddr LIKE '%Toledo%'
         OR shipaddr LIKE '%Toledo%'
      

      这将返回每一行(因为它总是正确的),所以没有......

      【讨论】:

        猜你喜欢
        • 2019-12-20
        • 1970-01-01
        • 1970-01-01
        • 2020-06-20
        • 2010-09-30
        • 2012-10-15
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多