sql >> Databáze >  >> RDS >> PostgreSQL

Jak použít více příkazů WITH v jednom dotazu PostgreSQL?

Podle ostatních komentářů před druhým společným tabulkovým výrazem [CTE] je čárka, nikoli výraz WITH, takže

WITH cte1 AS (SELECT...)
, cte2 AS (SELECT...)
SELECT *
FROM
    cte1 c1
    INNER JOIN cte2 c2
    ON ........

Pokud jde o váš skutečný dotaz, tato syntaxe by měla fungovat v PostgreSql, Oracle a sql-server, čím později budete obvykle pokračovat WITH se středníkem (;WTIH ), ale je to proto, že lidé z SQL serveru (včetně mě) neukončují předchozí příkazy, které je třeba ukončit před definováním CTE...

Všimněte si však, že jste měli druhý problém se syntaxí týkající se WHERE prohlášení. WHERE date IN table_2 není platné, protože ve skutečnosti nikdy neodkazujete na hodnotu/sloupec z tabulky_2. Preferuji INNER JOIN přes IN nebo Exists zde je syntaxe, která by měla fungovat s JOIN :

WITH table_1 AS (
SELECT GENERATE_SERIES('2012-06-29', '2012-07-03', '1 day'::INTERVAL) AS date
)

, table_2 AS (
SELECT GENERATE_SERIES('2012-06-30', '2012-07-13', '1 day'::INTERVAL) AS date
)

SELECT * 
FROM
     table_1 t1
     INNER JOIN 
     table_2 t2
     ON t1.date = t2.date
;

Pokud chcete zachovat způsob, jakým jste to měli, což by obvykle EXISTS bylo lepší než IN, ale k použití IN potřebujete skutečný příkaz SELECT ve vašem where.

SELECT * 
FROM
     table_1 t1
WHERE t1.date IN (SELECT date FROM table_2);

IN je velmi problematické, když date může být potenciálně NULL pokud tedy nechcete použít JOIN pak bych navrhoval EXISTS . následovně:

SELECT * 
FROM
     table_1 t1
WHERE EXISTS (SELECT * FROM table_2 t2 WHERE t2.date = t1.date);


  1. Úroveň izolace zavázaná ke čtení

  2. TNS-12505:TNS:listener aktuálně nezná SID uvedené v deskriptoru připojení

  3. Jak vytvořit pole JSON z databáze mysql

  4. 6 způsobů, jak přidat rok k datu v MariaDB