【发布时间】:2021-03-17 08:32:38
【问题描述】:
我正在使用 PostgreSQL v9.2.8 处理遗留系统我尝试运行查询:
SELECT ARRAY['a', 'b']::text[] && ARRAY['a', 'c', 'd']::text[];
最终出现错误:
ERROR: operator is not unique: text[] && text[]
LINE 1: select array['a', 'b']::text[] && array['a', 'c', 'd']::text...
^
HINT: Could not choose a best candidate operator. You might need to add explicit type casts.
与这里提出的许多关于类似问题的问题不同,类型是指定的,我在这里不能更明确。
我需要提一下扩展:btree_gin、btree_gist 和 intarray 已安装,但我无法为文本数组发现任何重复的运算符。
跑步:
SELECT oprname, oprcode,
l_arg.typname l_arg_type, l_arg.typcategory l_arg_cat,
r_arg.typname r_arg_type, r_arg.typcategory r_arg_cat
FROM pg_operator o
JOIN pg_namespace n ON n.oid = o.oprnamespace
join pg_type l_arg on l_arg.oid = o.oprleft
join pg_type r_arg on r_arg.oid = o.oprright
WHERE oprname ilike '%&&%'
显示:
| oprname | oprcode | l_arg_type | l_arg_cat | r_arg_type | r_arg_cat |
|---------|----------------|------------|-----------|------------|-----------|
| && | poly_overlap | polygon | G | polygon | G |
| && | box_overlap | box | G | box | G |
| && | tintervalov | tinterval | T | tinterval | T |
| && | circle_overlap | circle | G | circle | G |
| && | arrayoverlap | anyarray | P | anyarray | P |
| && | tsquery_and | tsquery | U | tsquery | U |
| && | range_overlaps | anyrange | P | anyrange | P |
| && | _int_overlap | _int4 | A | _int4 | A |
------------------------------------------------------------------------------
列出运营商家族:
SELECT am.amname AS index_method,
opf.opfname AS opfamily_name,
amop.amopopr::regoperator::text AS opfamily_operator
FROM pg_am am, pg_opfamily opf, pg_amop amop
WHERE opf.opfmethod = am.oid AND
amop.amopfamily = opf.oid
and amop.amopopr::regoperator::text ilike '%&&%'::text
ORDER BY index_method, opfamily_name, opfamily_operator;
表演
-------------------------------------------------------------
| index_method | opfamily_name | opfamily_operator |
|--------------|------------------|-------------------------|
| gin | array_ops | &&(anyarray,anyarray) |
| gin | gin__int_ops | &&(integer[],integer[]) |
| gist | box_ops | &&(box,box) |
| gist | circle_ops | &&(circle,circle) |
| gist | gist__int_ops | &&(integer[],integer[]) |
| gist | gist__intbig_ops | &&(integer[],integer[]) |
| gist | poly_ops | &&(polygon,polygon) |
| gist | range_ops | &&(anyrange,anyrange) |
-------------------------------------------------------------
这个问题是否与 &&(anyarray,anyarray) 和两个 &&(integer[],integer[]) 运营商之间的一些奇怪的冲突有关?
我最终想要实现的是创建一个两列 gin 索引
CREATE INDEX concurrently public_some_table_index
ON public.some_table
USING gin
( (array[text_col_01, text_col_02]) COLLATE pg_catalog."default" _text_ops );
应该用在类似的查询中
SELECT * FROM public.some_table foo
WHERE
(array[foo.text_col_01, foo.text_col_02]) && array['abc', 'def', 'ghi', 'jkl']::text[]
索引创建结果很好。如上所述,仅在查询中使用 && 会失败。
更新:
按照jjanes 的建议,在恢复架构转储 (pg_dump -s) 后,我检查了 Postgresql 9.2.8 的全新安装。问题依然存在。
【问题讨论】:
-
对于它的价值:您的代码在 Postgres 9.5 中工作(这是 dbfiddle 上最旧的可用版本):dbfiddle.uk/…。有升级计划吗?
-
是的,我相信这与此特定服务器的配置/扩展有关。我只是没有想法可以检查。还是谢谢。
-
我无法在 9.2.24 中仅使用您提到的 3 个扩展来重现这一点。如果您使用
pg_dump -s转储并恢复到新的 9.2 实例,它会在那里重现吗? -
您正在使用的 9.2 实例的次要版本是什么?
-
@AdrianKlaver 次要版本是 9.2.8 我会尽可能用新的实例检查这个。
标签: sql postgresql indexing operators postgresql-9.2