2010-03-25 31 views
9

这两种说法有完全不同的表现:MySQL中!col和col = false有什么区别?

mysql> explain select * from jobs where createIndexed=false; 
+----+-------------+-------+------+----------------------+----------------------+---------+-------+------+-------+ 
| id | select_type | table | type | possible_keys  | key     | key_len | ref | rows | Extra | 
+----+-------------+-------+------+----------------------+----------------------+---------+-------+------+-------+ 
| 1 | SIMPLE  | jobs | ref | i_jobs_createIndexed | i_jobs_createIndexed | 1  | const | 1 |  | 
+----+-------------+-------+------+----------------------+----------------------+---------+-------+------+-------+ 
1 row in set (0.01 sec) 

mysql> explain select * from jobs where !createIndexed; 
+----+-------------+-------+------+---------------+------+---------+------+-------+-------------+ 
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra  | 
+----+-------------+-------+------+---------------+------+---------+------+-------+-------------+ 
| 1 | SIMPLE  | jobs | ALL | NULL   | NULL | NULL | NULL | 17996 | Using where | 
+----+-------------+-------+------+---------------+------+---------+------+-------+-------------+ 

列定义和相关指标用于帮助分析:

createIndexed tinyint(1) NOT NULL DEFAULT 0, 
create index i_jobs_createIndexed on jobs(createIndexed); 

回答

3

MySQL不能使用索引为WHERE !createIndexed,因为它需要为每一行评估NOT createIndexed ,与表扫描。

5

从逻辑上讲,这些操作是相同的,但MySQL的优化器只是不那么聪明,看到NOT createIndexed中的createIndexed = 0

MySQLFALSE只是一个代名词0TRUE1的代名词。

此条件为假:

SELECT 2 = TRUE 

-- 
0 

,所以第一查询仅仅是一个纯指数ref比较0其中MySQL意识到,而第二个包含更复杂的逻辑MySQL不能代表作为可靠的表达。

+0

+1为清楚和技术性的解释。 – 2010-03-25 16:28:59

+0

+1表示优化器 – 2010-03-25 16:36:41

+0

MySQL优化器太弱了,我很惊讶 – Mask 2010-03-25 16:41:34

0

在MySQL中,FALSE关键字不是布尔一块数据:它是一个integer constant that equals zero。反之, ! (aka NOT)是一个逻辑运算符:

结果为1,如果操作数是0, 0,如果操作数是非零和NOT NULL 返回NULL。

我想,没有太多的实际差别:

mysql> select 1=0, 0=0, 33=0, null=0, not 1, not 0, not 33, not null; 
+-----+-----+------+--------+-------+-------+--------+----------+ 
| 1=0 | 0=0 | 33=0 | null=0 | not 1 | not 0 | not 33 | not null | 
+-----+-----+------+--------+-------+-------+--------+----------+ 
| 0 | 1 | 0 | NULL |  0 |  1 |  0 |  NULL | 
+-----+-----+------+--------+-------+-------+--------+----------+ 
1 row in set (0.00 sec) 

然而,他们没有相同的操作。

相关问题