📜  PostgreSQL – 自联接

📅  最后修改于: 2022-05-13 01:57:15.140000             🧑  作者: Mango

PostgreSQL – 自联接

PostgreSQL 有一种称为 SELF JOIN 的特殊连接类型,用于将表与其自身连接。在比较同一表中的行列时,它会派上用场。由于在PostgreSQL中不允许使用相同的表名进行比较,因此我们在自联接时使用别名来设置同一个表的不同名称。

同样重要的是要注意,没有像 SELF JOIN 这样的关键字,但它是在使用别名的 LEFT JOIN、RIGHT JOIN 或 INNER JOIN 的帮助下实现的。

Syntax:
SELECT column_list
FROM table_name T1
INNER JOIN table_name T2 ON join_predicate;

or,

Syntax:
SELECT column_list
FROM table_name T1
LEFT JOIN table_name T2 ON join_predicate;

or,

Syntax:
SELECT column_list
FROM table_name T1
RIGHT JOIN Table_name T2 ON join_predicate;

让我们建立一个示例数据库和表来演示自联接。

  • 使用以下命令创建名为“company”的数据库:
    CREATE DATABASE company;
  • 使用以下命令将“员工”表添加到数据库中以显示公司层次结构:
    CREATE TABLE employee (
        employee_id INT PRIMARY KEY,
        first_name VARCHAR (255) NOT NULL,
        last_name VARCHAR (255) NOT NULL,
        manager_id INT,
        FOREIGN KEY (manager_id) 
        REFERENCES employee (employee_id) 
        ON DELETE CASCADE
    );
  • 现在使用以下命令向表中添加一些员工数据:
    INSERT INTO employee (
        employee_id,
        first_name,
        last_name,
        manager_id
    )
    VALUES
        (1, 'Sandeep', 'Jain', NULL),
        (2, 'Abhishek ', 'Kelenia', 1),
        (3, 'Harsh', 'Aggarwal', 1),
        (4, 'Raju', 'Kumar', 2),
        (5, 'Nikhil', 'Aggarwal', 2),
        (6, 'Anshul', 'Aggarwal', 2),
        (7, 'Virat', 'Kohli', 3),
        (8, 'Rohit', 'Sharma', 3);

    manager_id列中的值表示员工向其报告的高级经理。如果是 Null,他/她不会向任何人报告。
    整体层次结构如下图所示:

    现在,我们已经设置好了数据库,让我们看看一些 SELF JOIN 的例子。
    示例 1:
    这里我们将使用同一个“employee”表两次查询who报告给谁的数据。



    SELECT
        e.first_name || ' ' || e.last_name employee,
        m .first_name || ' ' || m .last_name manager
    FROM
        employee e
    INNER JOIN employee m ON m .employee_id = e.manager_id
    ORDER BY
        manager;


    输出:

    示例 2:
    如果您还记得我们之前文章中使用的示例 DVD 租赁数据库,这里解释并可以从这里下载,我们将在该数据库的电影表中执行自连接。在这里,我们将查询具有相同运行时间的所有电影对。

    SELECT
        f1.title,
        f2.title,
        f1. length
    FROM
        film f1
    INNER JOIN film f2 ON f1.film_id <> f2.film_id
    AND f1. length = f2. length;

    输出: