1

最近将数据库从 MySQL 4 升级到 MySQL 5。以下查询现在已损坏:

SELECT COUNT(*) FROM Customer, Product INNER JOIN Orders 
ON (Customer.Email = Orders.Email)
WHERE NOT (Product.Flags & 8) AND 
    Customer.CustomerNumber = Product.CustomerNumber AND
    Truncate(Orders.ProductId/10, 0) = Truncate(Product.ProductId/10, 0)

收到以下错误:

#1054 - Unknown column 'Customer.Email' in 'on clause' 

我没有编写此查询,也不是 SQL 专家,但我猜测可能是 ANSI-89/ANSI-92 样式连接的混合,并且可能存在某种优先级问题。

你能解释一下这个错误,描述这个查询有什么问题,以及如何正确指定连接吗?

4

1 回答 1

6

JOIN语法中所述:

 在 MySQL 5.0.12 中加入处理更改

[删除]

以下列表提供了有关当前连接处理与旧版本中连接处理的几种效果的更多详细信息。“以前”一词的意思是“在 MySQL 5.0.12 之前”。</p>

[删除]
  • 以前,逗号运算符 ( ,) 和JOIN两者具有相同的优先级,因此连接表达式t1, t2 JOIN t3被解释为((t1, t2) JOIN t3)。NowJOIN具有更高的优先级,因此表达式被解释为(t1, (t2 JOIN t3)). 此更改会影响使用ON子句的语句,因为该子句只能引用连接操作数中的列,并且优先级的更改会更改对这些操作数的解释。

    例子:

    CREATE TABLE t1 (i1 INT, j1 INT);
    CREATE TABLE t2 (i2 INT, j2 INT);
    CREATE TABLE t3 (i3 INT, j3 INT);
    INSERT INTO t1 VALUES(1,1);
    INSERT INTO t2 VALUES(1,1);
    INSERT INTO t3 VALUES(1,1);
    SELECT * FROM t1, t2 JOIN t3 ON (t1.i1 = t3.i3);
    

    以前,SELECT由于 as 的隐式分组, 是合法t1,t2(t1,t2)。现在JOIN优先,所以ON子句的操作数是t2and t3。因为t1.i1不是任何一个操作数中的列,所以结果是Unknown column 't1.i1' in 'on clause'错误的。要允许处理连接,请将前两个表用括号显式分组,以便ON子句的操作数是(t1,t2)and t3

    SELECT * FROM (t1, t2) JOIN t3 ON (t1.i1 = t3.i3);
    

    或者,避免使用逗号运算符,JOIN而是使用:

    SELECT * FROM t1 JOIN t2 JOIN t3 ON (t1.i1 = t3.i3);
    

    此更改也适用于将逗号运算符与INNER JOIN, CROSS JOIN,LEFT JOIN和混合的语句RIGHT JOIN,所有这些语句现在都比逗号运算符具有更高的优先级。

于 2013-06-17T17:05:55.510 回答