这3个查询之间有什么区别?何处及;有-mysql版本吗?

这3个查询之间有什么区别?何处及;有-mysql版本吗?,mysql,Mysql,我这里的3个查询之间有什么区别? 第一个版本适用于我的本地主机xampp mysql数据库(10.1.9-MariaDB)。但是,它使用我的在线测试服务器mysql数据库(5.7.9-log mysql社区服务器GPL)检索0个结果。 第二个版本检索两台服务器的预期结果。但是在我的本地主机上,查询2检索相同的结果集,尽管顺序不同,但我猜这是因为我没有ORDERBY。 这是不同版本的mysql的问题吗?如果我的问题有什么不同的话,那又有什么不同呢? 查询1 SELECT s.eid,

我这里的3个查询之间有什么区别?

第一个版本适用于我的本地主机xampp mysql数据库(10.1.9-MariaDB)。但是,它使用我的在线测试服务器mysql数据库(5.7.9-log mysql社区服务器GPL)检索0个结果。

第二个版本检索两台服务器的预期结果。但是在我的本地主机上,查询2检索相同的结果集,尽管顺序不同,但我猜这是因为我没有ORDERBY。

这是不同版本的mysql的问题吗?如果我的问题有什么不同的话,那又有什么不同呢?

查询1

SELECT 
    s.eid, e.fname, e.lname, s.id, s.starttime, s.finishtime
FROM
    employees AS e
        RIGHT JOIN
    scheduling_shifts AS s USING (eid)
GROUP BY s.id
HAVING COUNT(s.date = '2016-01-15' OR NULL) > 0
    AND COUNT(s.eid = '1' OR NULL) = 0;
查询2

SELECT 
    s.eid, e.fname, e.lname, s.id, s.starttime, s.finishtime
FROM
    employees AS e
        RIGHT JOIN
    scheduling_shifts AS s USING (eid)
WHERE
    s.date = '2016-01-15'
GROUP BY s.id
HAVING COUNT(s.eid = '1' OR NULL) = 0;
编辑:: 查询3

此查询还检索正确的结果集减去NULL
s.eid

    SELECT 
    s.eid, e.fname, e.lname, s.id, s.starttime, s.finishtime
FROM
    employees AS e
        RIGHT JOIN
    scheduling_shifts AS s USING (eid)
WHERE
    s.date = '2016-01-15' AND s.eid <> '1'
选择
s、 eid,e.fname,e.lname,s.id,s.starttime,s.finishtime
从…起
雇员作为雇员
右连接
使用(eid)将_班次安排为s
哪里
s、 日期='2016-01-15'和s.eid'1'
这里有一个特定于我自己的查询的测试用例

目标是获取所选员工在所选日期的可能掉期列表。我们选择的日期是2016年1月15日,我们要调换班次的员工是员工
1
。列表无法获取自己的班次,因为他无法与自己交换班次。但它应该带来未分配的变化。(存在于
eid
NULL
的位置的移位)。因此,我们可以选择列出其他员工和他们的班次,或者当天未分配的班次,我们可以交换我们的班次

请注意,查询1-确实在这个问题上产生了正确的结果,确实在xampp(mariadb 10)上产生了正确的结果,但是没有在我的在线测试服务器上产生正确的结果

查询2也会获取正确的结果,并同时执行xampp和在线测试服务器

查询3获取所有分配的班次,但不获取未分配的班次


希望这能更好地解释我的问题。

其中
子句考虑每行的条件,
HAVING
子句考虑聚合,但我不认为这是造成差异的原因

使用“或NULL”会产生误导,在某些时候(如果不是现在)会产生意外或不正确的结果,请注意,COUNT()仅在表达式为非NULL时递增

下面,使用,我尝试显示效果:

CREATE TABLE Table1
    (`ID` int, `Other` varchar(4))
;

INSERT INTO Table1
    (`ID`, `Other`)
VALUES
    (1, 'ABC'),
    (2, 'DEF'),
    (3, NULL)
;
查询1

SELECT COUNT(`other` > '0' OR NULL)
FROM Table1
| COUNT(OTHER > '0' OR NULL) |
|----------------------------|
|                          2 |
SELECT COUNT(`other` > '0' OR `other` IS NULL)
FROM Table1
| COUNT(`other` > '0' OR `other` IS NULL) |
|-----------------------------------------|
|                                       3 |
| orig | x | y | z |
|------|---|---|---|
|    2 | 3 | 2 | 1 |

SELECT COUNT(`other` > '0' OR NULL)
FROM Table1
| COUNT(OTHER > '0' OR NULL) |
|----------------------------|
|                          2 |
SELECT COUNT(`other` > '0' OR `other` IS NULL)
FROM Table1
| COUNT(`other` > '0' OR `other` IS NULL) |
|-----------------------------------------|
|                                       3 |
| orig | x | y | z |
|------|---|---|---|
|    2 | 3 | 2 | 1 |
查询2

SELECT COUNT(`other` > '0' OR NULL)
FROM Table1
| COUNT(OTHER > '0' OR NULL) |
|----------------------------|
|                          2 |
SELECT COUNT(`other` > '0' OR `other` IS NULL)
FROM Table1
| COUNT(`other` > '0' OR `other` IS NULL) |
|-----------------------------------------|
|                                       3 |
| orig | x | y | z |
|------|---|---|---|
|    2 | 3 | 2 | 1 |

SELECT COUNT(`other` > '0' OR NULL)
FROM Table1
| COUNT(OTHER > '0' OR NULL) |
|----------------------------|
|                          2 |
SELECT COUNT(`other` > '0' OR `other` IS NULL)
FROM Table1
| COUNT(`other` > '0' OR `other` IS NULL) |
|-----------------------------------------|
|                                       3 |
| orig | x | y | z |
|------|---|---|---|
|    2 | 3 | 2 | 1 |
在我上面的查询1中,您可以看到,“或NULL”没有被计数,但在我的查询2中,表达式为所有行返回true,因此所有行都被计数

“OR NULL”是一个常量NULL,COUNT()不为NULL递增

[编辑] 我建议您使用
COUNT(*)
,因为您似乎只想对每一行进行计数,这正是
COUNT(*)
所做的,即不访问每一列,它所关心的只是“行是否存在”

[编辑2]顺便说一下

空通孔(不相等)的比较不起作用。NULL不能等于任何东西,因此也不可能知道它是否不相等(因为在它不相等之前,您必须知道它是否相等)

在以下结果中查看y和z列:

   SELECT
          COUNT(OTHER > '0' OR NULL) orig
        , COUNT(`other` > '0' OR `other` IS NULL) x
        , count(case when `other` <> 'abc' then NULL else 1 end) y
        , count(case when `other` <> 'abc' or `other` is null then NULL else 1 end) z
    FROM Table1

由于sqlfiddle测试用例可用,因此我将以这种方式构造查询。它列出了所提供的表中9行中的8行:

SELECT 
        s.eid, e.fname, e.lname, s.id, s.date, s.starttime, s.finishtime
FROM scheduling_shifts s
      LEFT JOIN employees AS e on s.eid = e.eid
WHERE (s.eid <> 1 OR s.eid is null)
      AND s.date = '2016-01-15';
选择
s、 eid,e.fname,e.lname,s.id,s.date,s.starttime,s.finishtime
从排班
在s.eid=e.eid上以e的身份左键加入员工
其中(s.eid 1或s.eid为空)
s.date='2016-01-15';

由于我无法复制您的特定问题(不同平台的不同结果),我很遗憾地说,只有您使用“或空”的行为让我觉得不寻常,并且可能产生不可预测的结果。查询的第二个特点是,在没有特殊原因的情况下使用having子句,我也会避免使用having子句。

WHERE
子句考虑每行的条件,
having
子句考虑聚合,但我不认为这是造成差异的原因

使用“或NULL”会产生误导,在某些时候(如果不是现在)会产生意外或不正确的结果,请注意,COUNT()仅在表达式为非NULL时递增

下面,使用,我尝试显示效果:

CREATE TABLE Table1
    (`ID` int, `Other` varchar(4))
;

INSERT INTO Table1
    (`ID`, `Other`)
VALUES
    (1, 'ABC'),
    (2, 'DEF'),
    (3, NULL)
;
查询1

SELECT COUNT(`other` > '0' OR NULL)
FROM Table1
| COUNT(OTHER > '0' OR NULL) |
|----------------------------|
|                          2 |
SELECT COUNT(`other` > '0' OR `other` IS NULL)
FROM Table1
| COUNT(`other` > '0' OR `other` IS NULL) |
|-----------------------------------------|
|                                       3 |
| orig | x | y | z |
|------|---|---|---|
|    2 | 3 | 2 | 1 |

SELECT COUNT(`other` > '0' OR NULL)
FROM Table1
| COUNT(OTHER > '0' OR NULL) |
|----------------------------|
|                          2 |
SELECT COUNT(`other` > '0' OR `other` IS NULL)
FROM Table1
| COUNT(`other` > '0' OR `other` IS NULL) |
|-----------------------------------------|
|                                       3 |
| orig | x | y | z |
|------|---|---|---|
|    2 | 3 | 2 | 1 |
查询2

SELECT COUNT(`other` > '0' OR NULL)
FROM Table1
| COUNT(OTHER > '0' OR NULL) |
|----------------------------|
|                          2 |
SELECT COUNT(`other` > '0' OR `other` IS NULL)
FROM Table1
| COUNT(`other` > '0' OR `other` IS NULL) |
|-----------------------------------------|
|                                       3 |
| orig | x | y | z |
|------|---|---|---|
|    2 | 3 | 2 | 1 |

SELECT COUNT(`other` > '0' OR NULL)
FROM Table1
| COUNT(OTHER > '0' OR NULL) |
|----------------------------|
|                          2 |
SELECT COUNT(`other` > '0' OR `other` IS NULL)
FROM Table1
| COUNT(`other` > '0' OR `other` IS NULL) |
|-----------------------------------------|
|                                       3 |
| orig | x | y | z |
|------|---|---|---|
|    2 | 3 | 2 | 1 |
在我上面的查询1中,您可以看到,“或NULL”没有被计数,但在我的查询2中,表达式为所有行返回true,因此所有行都被计数

“OR NULL”是一个常量NULL,COUNT()不为NULL递增

[编辑] 我建议您使用
COUNT(*)
,因为您似乎只想对每一行进行计数,这正是
COUNT(*)
所做的,即不访问每一列,它所关心的只是“行是否存在”

[编辑2]顺便说一下

空通孔(不相等)的比较不起作用。NULL不能等于任何东西,因此也不可能知道它是否不相等(因为在它不相等之前,您必须知道它是否相等)

在以下结果中查看y和z列:

   SELECT
          COUNT(OTHER > '0' OR NULL) orig
        , COUNT(`other` > '0' OR `other` IS NULL) x
        , count(case when `other` <> 'abc' then NULL else 1 end) y
        , count(case when `other` <> 'abc' or `other` is null then NULL else 1 end) z
    FROM Table1

由于sqlfiddle测试用例可用,因此我将以这种方式构造查询。它列出了所提供的表中9行中的8行:

SELECT 
        s.eid, e.fname, e.lname, s.id, s.date, s.starttime, s.finishtime
FROM scheduling_shifts s
      LEFT JOIN employees AS e on s.eid = e.eid
WHERE (s.eid <> 1 OR s.eid is null)
      AND s.date = '2016-01-15';
选择
s、 eid,e.fname,e.lname,s.id,s.date,s.starttime,s.fin