mysql - 列上没有相等运算符的sql自连接

标签 mysql join self-join

发布问题和有效的 SQL 解决方案。我的困惑是,当我过去进行自连接时,要连接的列中总是有一些相等的值(等于运算符),但在下面的示例中,自连接似乎可以在不使用等于运算符的情况下工作?在我下面的示例中,使用减号运算符和 >,没有等于运算符来指定用于连接的列。

想知道如果没有相等运算符,底层自连接在我的示例中是如何工作的?

问题,

给定一个天气表,编写一个 SQL 查询来查找与之前(昨天)的日期相比温度更高的所有日期的 ID。

+---------+------------+------------------+
| Id(INT) | Date(DATE) | Temperature(INT) |
+---------+------------+------------------+
|       1 | 2015-01-01 |               10 |
|       2 | 2015-01-02 |               25 |
|       3 | 2015-01-03 |               20 |
|       4 | 2015-01-04 |               30 |
+---------+------------+------------------+

例如,为上面的 Weather 表返回以下 Id:

+----+
| Id |
+----+
|  2 |
|  4 |
+----+

SQL解决方案,

select W1.Id
from Weather W1, Weather W2
where TO_DAYS(W1.Date)-TO_DAYS(W2.Date) = 1 and W1.Temperature > W2.Temperature

最佳答案

使用 ANSI 连接编写它,因为它们是 SQL 的标准部分:

select W1.Id
from Weather W1
        inner join
     Weather W2
        on TO_DAYS(W1.Date)-TO_DAYS(W2.Date) = 1 and
           W1.Temperature > W2.Temperature

(应该产生相同的结果集)

联接只是匹配两组行的过程 - 您在联接的“左侧”有一个行源,在联接的“右侧”有一个行源。在一般情况下,这些行源是表,但连接也可以连接任何先前连接的结果作为行源。

理论上,在联接中,结果将是笛卡尔积 - 左侧的每一行都将与右侧的每一行 匹配。如果这是您想要的,您可以使用 CROSS JOIN 进行指示。

但是,通常我们希望限制连接的结果小于行的笛卡尔积。我们通过编写 ON 子句(或在您的示例中的 WHERE 子句中使用旧式逗号连接)来表达这些限制。

常见的联接类型是等值联接,其中比较每一侧的一个或多个列是否相等。但这绝不是必需的。它可以是任何有意义的谓词。例如。我半定期使用的一种连接形式我将其描述为“三角连接”(绝不是标准术语),其中每一行都与后面的 every 行匹配:

SELECT
    *
FROM
    Table t1
        left join
    Table t2
        on
           t1.ID < t2.ID

这完全没问题。 中具有最低ID 的行将与表中的所有 行匹配。具有最高 ID 值的行将不会与 任何 其他行匹配。

关于mysql - 列上没有相等运算符的sql自连接,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43316374/

相关文章:

java - 如何在Hibernate中定义非生成的主键字段

mysql - 带有 `from A inner join B ...LIMIT x,y` 的 MySQL 查询是在从表 A 中获取 y 行之前还是之后执行连接?

ruby-on-rails - ActiveRecord 中多个自连接的多对多关联

mysql - 连接两个表未按预期工作

php - MySQL:如何查询获取特定位置的记录?

mysql - 无法在 Azure Mysql DB 中创建触发器

mysql - nodejs mysql 将事件的值传递给另一个事件

mysql - 理解加盟

MySQL 联合和连接

php - 同一张表上的相关项目