如何将JSON数组转换为文本数组?

Pet*_*uss 6 arrays postgresql json

此解决方法不起作用

CREATE FUNCTION json_array_castext(json) RETURNS text[] AS $f$
  SELECT array_agg(x::text) FROM json_array_elements($1) t(x);
$f$ LANGUAGE sql IMMUTABLE;

-- Problem:
SELECT 'hello'='hello';  -- true...
SELECT  (json_array_castext('["hello","world"]'))[1] = 'hello'; -- false!
Run Code Online (Sandbox Code Playgroud)

那么,如何获取文本的真实数组?

PS:使用所谓的“头等公民” JSONb,同样的问题。


编辑:@OtoShavadze好的答案(注释已解决!)之后,PostgreSQL开发人员清单为什么x::text进行强制转换(使用第9.5.6页),为什么它不生成警告或错误?

Oto*_*dze 5

尝试使用 json_array_elements_text而不是json_array_elements,并且不需要显式转换为text(x::text),因此可以使用:

CREATE or replace FUNCTION json_array_castext(json) RETURNS text[] AS $f$
    SELECT array_agg(x) FROM json_array_elements_text($1) t(x);
$f$ LANGUAGE sql IMMUTABLE;
Run Code Online (Sandbox Code Playgroud)

对于您的其他问题

为什么x :: text不是强制转换?

这是强制转换的,因此,它不会产生任何错误,但是在将json字符串强制转换为以下文本时:::textpostgres在值中添加引号。

仅出于测试目的,让我们再次将功能更改为原始功能(如您的问题所述),然后尝试:

SELECT  
(json_array_castext('["hello","world"]'))[1] = 'hello',
(json_array_castext('["hello","world"]'))[1],
'hello'
Run Code Online (Sandbox Code Playgroud)

如您所见, (json_array_castext('["hello","world"]'))[1]给出"hello"而不是hello。这就是您false比较这些值时得到的原因。


Tom*_*Yeh 2

CREATE or replace FUNCTION json_to_array(json) RETURNS text[] AS $f$
  SELECT coalesce(array_agg(x), 
    CASE WHEN $1 is null THEN null ELSE ARRAY[]::text[] END)
  FROM json_array_elements_text($1) t(x);
$f$ LANGUAGE sql IMMUTABLE;
Run Code Online (Sandbox Code Playgroud)

测试用例:

  • select json_to_array('["abc"]')=> 一个元素数组
  • select json_to_array('[]')=> 一个空数组
  • select json_to_array(null)=> 空