6

我有这张桌子:

select count(distinct clean_deep_link) from tbl_1;
+---------------------------------+
| count(distinct clean_deep_link) |
+---------------------------------+
|                          121211 |
+---------------------------------+

我有这个查询:

select count(1) from tbl_1 where clean_deep_link IN
  (select clean_deep_link from tbl_2);

+----------+
| count(1) |
+----------+
|    66360 |
+----------+

但是当我将查询更改为它时,not in它返回一个空集:

select count(1) from tbl_1
where clean_deep_link not in (select clean_deep_link from tbl_2);
+----------+
| count(1) |
+----------+
|        0 |
+----------+

这怎么可能?如果子查询包含大约一半的记录,not子查询的不应该包含另一半吗?我在这里想念什么?

谢谢

4

3 回答 3

9

我会假设这tbl_1.clean_deep_linkNULL其余的行。

这些值既不是您的子查询,IN也不是NOT IN您的子查询。


另一个原因可能是,您NULLtbl_2.clean_deep_link.

请尝试以下方法:

select count(1) from tbl_1
where clean_deep_link not in (select clean_deep_link
                              from tbl_2 WHERE clean_deep_link IS NOT NULL);

问题NULL在于它既不是=,也不是<>任何其他值(包括NULL)。

在检查时NOT IN,MySQL 需要检查每个值,tbl_1因为它不包含在tbl_2其中并因此检查它们是否存在<>

你的价值观不是 <> NULL,所以他们不是 NOT IN

另请参阅:对空值使用 NOT IN 运算符


检查SQL Fiddle中的示例。

于 2012-05-16T07:38:53.460 回答
2

MySQL 中的NULL列被计为不同的,因此三个NULL值都被认为是不同的。

如其他地方所述,您无法NULL使用传统的比较运算符与其他值进行比较,IN其中NOT IN.

以下运算符可以处理NULL

x <=> y - returns 1 if x == y (even if both are NULL)
x IS NULL - returns 1 if x is null
x IS NOT NULL - returns 0 if x is null
于 2012-05-16T07:45:26.910 回答
0
SELECT COUNT(*) - COUNT(1) 
FROM tbl_1 
WHERE clean_deep_link IN (
    SELECT clean_deep_link 
    FROM tbl_2
);
于 2012-05-16T07:49:02.543 回答