2015-11-03 18 views
4

如果我有一個像PostgreSQL在FROM子句中的json_array_elements - 爲什麼這不是笛卡爾連接?

SELECT t.json_column->>'x', 
    nested->>'y' 
FROM my_table t, 
    json_array_elements(t->'nested') nested 

表達我爲什麼不需要加入?更確切地說,爲什麼這不像笛卡爾CROSS JOIN

它看起來像一個連接通過引用json_array_elements調用中的表別名t而隱式發生。但是具有表函數的隱式連接語法對我來說並不熟悉。

在PostgreSQL或其他數據庫中是否還有其他類似SQL語法的例子?

+1

*爲什麼它沒有像笛卡爾加入?*因爲,這實際上是一個隱含[橫向](http://www.postgresql.org/docs/current/static/queries-table-expressions.html#查詢,這側向)[JOIN](https://wiki.postgresql.org/wiki/What's_new_in_PostgreSQL_9.3#LATERAL_JOIN)(它總是會發生的,如果你使用'FROM'子句中的函數) – pozs

回答

4

事實上,這是老式語法CROSS JOIN。正式等價物:

SELECT 
    t.json_column->>'x', 
    nested->>'y' 
FROM 
    my_table t 
CROSS JOIN 
    json_array_elements(t.json_column->'nested') nested; 

該查詢不會產生笛卡爾積,但其行爲更像是內連接。這是因爲它有一個隱藏的兩部分連接之間的引用,在這種情況下,別名爲t。這種連接被稱爲LATERAL JOIN。對於the documentation

當FROM項包含LATERAL交叉引用,評價如下進行:針對的每一行FROM項目提供所述交叉引用列(S),或設置多個的行的從提供的項目列,LATERAL項目使用行或行集合的列值進行評估。生成的行像往常一樣與它們的計算行相結合。這對於列源表中的每一行或一組行是重複的。

如果某個連接的某個部分是一個函數,那麼默認情況下它將被視爲橫向。

+0

對不起,我應該已經更確切。我知道'從a,b'是一個連接 - 我真正的問題是爲什麼這不像一個笛卡爾/交叉連接。在表函數的工作方式上可能會有些神奇。 – wrschneider

+0

是的,我應該猜到了。見編輯的答案。 – klin

+0

也有用「橫向子查詢」 http://www.postgresql.org/docs/9.4/static/queries-table-expressions.html」 – wrschneider