PostgreSQL 9.5以上的版本中有了很多方便的操作符,使得操作 JSON 變得非常方便了。
一、 -> 和 ->> :
-> 表示獲取一個JSON數組元素,支持下標值(下標從0開始)、Key獲取。->> 表示獲取一個JSON對象字符串。
代碼:
SELECT '[{"a":1},{"b":2},{"c":3}]'::JSON -> 1; 結果: {"b":2}
以上,::JSON 表示聲明前面的字符串為一個JSON字符串對象,而且PostgreSQL中的JSON、JSONB對象 Key的聲明必須是字符串 。同時,1表示獲取JSON數組中下標值為1的JSON對象。
接下來,看下 ->> 的用法:
代碼: SELECT '[{"a":1},{"b":2},{"c":3}]'::JSON ->> 1; 結果: {"b":2}
以上,->> 的查詢結果和 -> 對比不太直觀,我們可以進一步驗證。
代碼:
SELECT '[{"a":1},{"b":2},{"c":3}]'::JSON -> 1 -> 'b'; 結果: 2
以上,我們可以看到首先我們使用下標的方式,獲取JSON數組中下標值為1的JSON對象 {"b":2}。然后,我們通過Key的方式來獲取這個JSON對象的Value值,結果是 2。
接下來,我們測試下 ->> 的方式來獲取:
代碼:
SELECT '[{"a":1},{"b":2},{"c":3}]'::JSON ->> 1 -> 'b'; 報錯: [SQL]SELECT '[{"a":1},{"b":2},{"c":3}]'::JSON ->> 1 -> 'b'; [Err] 錯誤: 操作符不存在: text -> unknown LINE 1: SELECT '[{"a":1},{"b":2},{"c":3}]'::JSON ->> 1 -> 'b'; ^ HINT: No operator matches the given name and argument types. You might need to add explicit type casts.
以上,可以看到錯誤提示操作符不存在,因為第一步查詢出來的是一個字符串,不是JSON對象。當然,我們可以改造下這個查詢語句:
代碼:
SELECT ('[{"a":1},{"b":2},{"c":3}]'::JSON ->> 1)::JSON -> 'b'; 結果: 2
以上,可以看到現在可以正確查詢出結果,我們將第一步查詢出來的字符串轉成JSON對象,然后通過 Key 的方式來獲取 Value。不過,這種查詢方式相對於 -> 來說還是比較繁瑣的。
二、 #> 和 #>> :
在前一步,我們在一個JSON數組中可以使用 -> 下標值的方式來獲取一個JSON對象。但是,如果我們我們檢索的不是JSON數組,而是一個JSON對象中的JSON對象。很顯然,這種下標獲取的方式不再適用。不過,我們可以使用下面的方式來獲取。
#> 表示獲取指定路徑的一個JSON對象,#>>表示獲取指定路徑的一個JSON對象的字符串。
代碼:
SELECT '{"a":1,"b":{"ba":"b1","bb":"b2"},"c":3}'::JSON #> '{b}' 結果: {"ba":"b1","bb":"b2"}
以上,我們使用 #> 方式來獲取一個JSON對象中的JSON對象。
注意:
在獲取一個JSON對象時,除非是JSON數組中的下標,必須要要用 { } 將JSON對象的 Key 包裹起來,否則會拋出異常。
代碼:
SELECT '{"a":1,"b":{"ba":"b1","bb":"b2"},"c":3}'::JSON#>'b' 結果: [SQL]SELECT '{"a":1,"b":{"ba":"b1","bb":"b2"},"c":3}'::JSON#>'b' [Err] 錯誤: 有缺陷的數組常量:"b" LINE 1: SELECT '{"a":1,"b":{"ba":"b1","bb":"b2"},"c":3}'::JSON#>'b' ^ DETAIL: 數組值必須以 "{" 或者維度信息開始。
同樣的,我們還可以在 #> 的基礎上,繼續獲取這個JSON對象內的相關信息。
代碼:
SELECT '{"a":1,"b":{"ba":"b1","bb":"b2"},"c":3}'::JSON#>'{b}'->'ba' 結果: "b1"
以上,可以看到 -> 獲取的是一個JSON對象。