'false'可以匹配mysql中的某些字符串吗?

时间:2011-12-03 17:11:24

标签: mysql

我有一张这样的表:

CREATE TABLE IF NOT EXISTS `session` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `token` varchar(32) NOT NULL,
  `profile` varchar(1000) NOT NULL,
  `created_time` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
  PRIMARY KEY (`id`)
) ENGINE=MyISAM  DEFAULT CHARSET=utf8 AUTO_INCREMENT=41 ;

以及此表中的一些数据:

(38, '395d5feaf28df01aafe0781a7f34acbe', 'a:3:{s:2:"id";s:1:"2";s:8:"username";s:7:"wanmeng";s:12:"created_time";s:19:"2011-11-18 19:37:33";}', '2011-12-03 14:14:35'),
(39, '0e0ca06ed9ad86937f190eb9544ac935', 'a:3:{s:2:"id";s:1:"1";s:8:"username";s:6:"delphi";s:12:"created_time";s:19:"2011-11-18 13:29:40";}', '2011-12-03 14:28:36'),
(31, '3cba76b97cf123009632bdaa5a306385', 'a:3:{s:2:"id";s:1:"1";s:8:"username";s:6:"delphi";s:12:"created_time";s:19:"2011-11-18 13:29:40";}', '2011-12-02 15:50:21'),
(30, 'fa356333dd3ee8f1b18b8bf0a827e34c', 'a:3:{s:2:"id";s:1:"1";s:8:"username";s:6:"delphi";s:12:"created_time";s:19:"2011-11-18 13:29:40";}', '2011-12-01 15:32:47')

当我执行查询时:SELECT * FROM session WHERE token = false,我希望没有返回结果,但是mysql返回结果:

39  0e0ca06ed9ad86937f190eb9544ac935    a:3:{s:2:"id";s:1:"1";s:8:"username";s:6:"delphi";...   2011-12-03 22:28:36
30  fa356333dd3ee8f1b18b8bf0a827e34c    a:3:{s:2:"id";s:1:"1";s:8:"username";s:6:"delphi";...   2011-12-01 23:32:47

似乎布尔值'false'可以匹配某些varchar,但是'fa356333dd3ee8f1b18b8bf0a827e34c'和'false'之间是否存在任何关系,为什么会这样?

4 个答案:

答案 0 :(得分:5)

在MYSQL中,FALSE不是布尔值,它是一个整数,更具体地说是零。事实上,MySQL没有布尔列类型(它有BOOLBOOLEAN,但它们只是TINYINT的别名。因此,您的查询是以下内容的同义词:

SELECT * FROM session WHERE token = 0

由于token是VARCHAR,因此MySQL需要将字符串转换为数字。运行此查询,您将了解规则:

SELECT
    0 + "0001",
    0 + "123abc",
    0 + "abc123"

因此,fa356333dd3ee8f1b18b8bf0a827e34c会转换为0因为它以字母开头,因此匹配。

答案 1 :(得分:2)

您是否有任何理由未对token is nulltoken like ''进行测试?将varchar与false进行比较是一个坏主意,无论数据库是否会捕获您的错误...... varchar永远不会为false,false不等于null。

答案 2 :(得分:2)

如果要将布尔值与varchar进行比较,MySQL必须进行一些隐式类型转换。 MySQL将varchar值转换为布尔值,仅检查第一个字符。

如果字符是字符或数字0,则字符串将被计算为0,因此为假 如果字符是不同于0的数字,则字符串的计算结果为1,因此为True(并且不会出现在结果集中)

唯一要做的就是不要将字符串与布尔值进行比较,因为它没有任何意义。

答案 3 :(得分:1)

这应该是评论,但我没有足够的声誉......所以......

DelphiQin,您在评论中说,您正在将CI“get()”方法的结果传递给查询参数。我一直在那里,我通过在传递给查询之前将变量转换为字符串来解决:

(string)$my_var

这样,它将使用''(空字符串)而不是布尔值假。

我希望它可以帮助有同样问题的人。