PostgreSQL子查詢


子查詢或內部查詢或巢狀查詢是一個PostgreSQL查詢中的查詢,它可以嵌入到WHERE子句中。子查詢用於返回將在主查詢中使用的資料作為進一步限制要檢索的資料的條件。
子查詢可以與SELECTINSERTUPDATEDELETE語句以及運算子(如=<>>=<=IN等)一起使用。

子查詢必須遵循以下規則:

  • 子查詢必須括在括號中。
  • 子查詢在SELECT子句中只能有一列,除非主查詢中有多個列用於比較其所選列的子查詢。
  • ORDER BY不能用於子查詢,儘管主查詢可以使用ORDER BYGROUP BY可用於執行與子查詢中的ORDER BY相同的功能。
  • 返回多行的子查詢只能與多個值運算子一起使用,例如:INEXISTSNOT INANY / SOMEALL運算子。
  • BETWEEN運算子不能與子查詢一起使用; 但是,BETWEEN可以在子查詢中使用。

帶SELECT語句的子查詢

子查詢最常用於SELECT語句。 基本語法如下:

SELECT column_name [, column_name ]
FROM   table1 [, table2 ]
WHERE  column_name OPERATOR
      (SELECT column_name [, column_name ]
      FROM table1 [, table2 ]
      [WHERE])

範例:

考慮COMPANY表有以下記錄:

 id | name  | age | address   | salary
----+-------+-----+-----------+--------
  1 | Paul  |  32 | California|  20000
  2 | Allen |  25 | Texas     |  15000
  3 | Teddy |  23 | Norway    |  20000
  4 | Mark  |  25 | Rich-Mond |  65000
  5 | David |  27 | Texas     |  85000
  6 | Kim   |  22 | South-Hall|  45000
  7 | James |  24 | Houston   |  10000
(7 rows)

現在,我們用SELECT語句檢查以下子查詢:

yiibai_db=# SELECT *
     FROM COMPANY
     WHERE ID IN (SELECT ID
                  FROM COMPANY
                  WHERE SALARY > 45000) ;

這將產生以下結果:

 id | name  | age |  address    | salary
----+-------+-----+-------------+--------
  4 | Mark  |  25 | Rich-Mond   |  65000
  5 | David |  27 | Texas       |  85000
(2 rows)

帶INSERT語句的子查詢

子查詢也可以用於INSERT語句。INSERT語句使用從子查詢返回的資料插入另一個表。 可以使用任何字元,日期或數位函式修改子查詢中選定的資料。

基本語法如下:

INSERT INTO table_name [ (column1 [, column2 ]) ]
           SELECT [ *|column1 [, column2 ]
           FROM table1 [, table2 ]
           [ WHERE VALUE OPERATOR ]

範例:

考慮一個表COMPANY_BKP,其結構與COMPANY表類似,可以使用COMPANY_BKP作為表名使用相同的CREATE TABLE資料結構來建立。 現在要將完整的COMPANY表複製到COMPANY_BKP中,以下是語句:

yiibai_db=# INSERT INTO COMPANY_BKP
     SELECT * FROM COMPANY
     WHERE ID IN (SELECT ID
                  FROM COMPANY) ;

帶UPDATE語句的子查詢:

子查詢可以與UPDATE語句一起使用。 當使用具有UPDATE語句的子查詢時,可以更新表中的單列或多列。

UPDATE table
SET column_name = new_value
[ WHERE OPERATOR [ VALUE ]
   (SELECT COLUMN_NAME
   FROM TABLE_NAME)
   [ WHERE) ]

範例:

假設我們有一個名為COMPANY_BKP表,它是COMPANY表的備份。

以下範例將所有客戶(其AGE大於或等於27)在COMPANY表中的SALARY更新為0.50倍:

testdb=# UPDATE COMPANY
     SET SALARY = SALARY * 0.50
     WHERE AGE IN (SELECT AGE FROM COMPANY_BKP
                   WHERE AGE >= 27 );

這將影響兩行,最後COMPANY表中將具有以下記錄:

id | name  | age | address     | salary
----+-------+-----+-------------+--------
  2 | Allen |  25 | Texas       |  15000
  3 | Teddy |  23 | Norway      |  20000
  4 | Mark  |  25 | Rich-Mond   |  65000
  6 | Kim   |  22 | South-Hall  |  45000
  7 | James |  24 | Houston     |  10000
  1 | Paul  |  32 | California  |  10000
  5 | David |  27 | Texas       |  42500
(7 rows)

帶有DELETE語句的子查詢:

子查詢可以與DELETE語句一起使用,就像上面提到的任何其他語句一樣。

基本語法如下:

DELETE FROM TABLE_NAME
[ WHERE OPERATOR [ VALUE ]
   (SELECT COLUMN_NAME
   FROM TABLE_NAME)
   [ WHERE) ]

範例:

假設我們有一個COMPANY_BKP表,它是COMPANY表的備份。

以下範例從COMPANY 表中刪除所有客戶的記錄,其AGE大於或等於27資料記錄:

testdb=# DELETE FROM COMPANY
     WHERE AGE IN (SELECT AGE FROM COMPANY_BKP
                   WHERE AGE > 27 );

這將影響兩行,最後COMPANY表將具有以下記錄,查詢結果如下:

 id | name  | age | address     | salary
----+-------+-----+-------------+--------
  2 | Allen |  25 | Texas       |  15000
  3 | Teddy |  23 | Norway      |  20000
  4 | Mark  |  25 | Rich-Mond   |  65000
  6 | Kim   |  22 | South-Hall  |  45000
  7 | James |  24 | Houston     |  10000
  5 | David |  27 | Texas       |  42500
(6 rows)