这是我(也许通常适合你)的非优化解决方案:
使用非优化内部函数的PG问题的解决方法:
CREATE FUNCTION unnest_with_idx(anyarray)
RETURNS TABLE(idx integer, val anyelement) AS
$$
SELECT generate_series(1,array_upper($1,1)) as idx, unnest($1) as val;
$$ LANGUAGE SQL IMMUTABLE;
Run Code Online (Sandbox Code Playgroud)
测试:
SELECT idx,val from unnest_with_idx(array[1,20,3,5]) as t;
Run Code Online (Sandbox Code Playgroud)
但是,正如我所说,非优化.我不敢相信(!!)PostgreSQL没有数组的内部索引......?但在这种情况下,问题是如何直接访问这个GIN类内部计数器的指数?
注1:上面的解决方案和问题与" 如何通过数组的每个元素创建索引? "不同.也可以与" Can PostgreSQL索引数组列? "不同,因为该函数用于隔离数组,而不是用于数组字段的表索引.
NOTE2(在答案后编辑):"数组索引"(更常用的术语)或"数组下标"或"数组计数器"是我们可以在语义路径中使用的术语,用于将"内部计数器",累加器引用到下一个数组项目.我看到没有PostgreSQL命令提供对此计数器的直接访问.作为generate_series()函数,generate_subscripts()函数是序列生成器,并且性能(最好但是)接近相同.通过其他手工row_number()功能提供了对"内部行计数器"的直接访问,但它是关于行,而不是关于数组,不幸的是性能更差.
我正在实现一个Query系统.我实现了不需要的功能.现在用户询问在单个select语句中使用多个unfst.我使用PostgreSQL作为指南,因为大多数用户在我们的查询系统之前使用它.
PostgreSQL有这样奇怪的行为:
postgres=# select unnest(array[1,2]), unnest(array[1,2]);
unnest | unnest
--------+--------
1 | 1
2 | 2
(2 rows)
postgres=# select unnest(array[1,2]), unnest(array[1,2,3]);
unnest | unnest
--------+--------
1 | 1
2 | 2
1 | 3
2 | 1
1 | 2
2 | 3
(6 rows)
Run Code Online (Sandbox Code Playgroud)
我的实现总是生成笛卡尔积.我想知道,这背后的正确逻辑是什么?PostgreSQL正在做正确的事还是只是一个bug?我没有在ANSI文档或PostgreSQL文档中找到明确的描述.
我有一列numeric[]都具有相同大小的值。我想对它们进行元素平均。我的意思是说
{1, 2, 3}, {-1, -2, -3}, and {3, 3, 3}
Run Code Online (Sandbox Code Playgroud)
应该是{1, 1, 1}。同样有趣的是如何对这些元素进行总和,尽管我希望一个解决方案将是另一个解决方案。
(NB: The length of the arrays is fixed within a single table, but may vary between tables. So I need a solution which doesn't assume a certain length.)
My initial guess is that I should be using unnest somehow, since unnest applied to a numeric[] column flattens out all the arrays. So I'd like to think that there's a nice way to …
我有一张这样的桌子;
CREATE TABLE test (
id BIGSERIAL PRIMARY KEY,
data JSONB
);
INSERT INTO test(data) VALUES('[1,2,"a",4,"8",6]'); -- id = 1
INSERT INTO test(data) VALUES('[1,2,"b",4,"7",6]'); -- id = 2
Run Code Online (Sandbox Code Playgroud)
如何更新元素data->1,并data->3为其他的东西没有PL/*?
我有关系
+-----+----+
| seq | id |
+-----+----+
| 1 | A1 |
| 2 | B1 |
| 3 | C1 |
| 4 | D1 |
+-----+----+
Run Code Online (Sandbox Code Playgroud)
并希望将其加入 PostgreSQL
+----+-------+
| id | alter |
+----+-------+
| B1 | B2 |
| D1 | D2 |
+----+-------+
Run Code Online (Sandbox Code Playgroud)
所以我得到了所有可能的替换组合(即或多或少替换的笛卡尔积)。所以第1组没有更新,第2组只有B2,第3组只有D2,第4组有B2和D2。
结尾应该像这样,但应该对更多人开放(例如 D1 的额外 D3)
+-------+-----+----+
| group | seq | id |
+-------+-----+----+
| 1 | 1 | A1 |
| 1 | 2 | B1 |
| 1 | …Run Code Online (Sandbox Code Playgroud) 我有如下数据。
id col1[]
--- ------
1 {1,2,3}
2 {3,4,5}
Run Code Online (Sandbox Code Playgroud)
我的问题是如何在数组中使用替换函数。
select array_replace(col1, 1, 100) where id = 1;
Run Code Online (Sandbox Code Playgroud)
但它给出了一个错误,如:
function array_replace(integer[], integer, integer) does not exist
Run Code Online (Sandbox Code Playgroud)
谁能建议如何使用它?
当一个表不是数组值而另一个表的数组值可以包含多个值时,我似乎无法找到通过数组列连接两个表的技巧。当存在单值数组时,它确实有效。
这是我正在谈论的一个简单的最小示例。真实的表在数组列 FWIW 上有 GIN 索引。这些没有,但查询的行为相同。
DROP TABLE IF EXISTS eg_person;
CREATE TABLE eg_person (id INT PRIMARY KEY, name TEXT);
INSERT INTO eg_person (id, name) VALUES
(1, 'alice')
, (2, 'bob')
, (3, 'charlie');
DROP TABLE IF EXISTS eg_assoc;
CREATE TABLE eg_assoc (aid INT PRIMARY KEY, actors INT[], benefactors INT[]);
INSERT INTO eg_assoc (aid, actors, benefactors) VALUES
(1, '{1}' , '{2}')
, (2, '{1,2}', '{3}')
, (3, '{1}' , '{2,3}')
, (4, '{4}' , '{1}');
SELECT aid, actors, a_person.name, benefactors, …Run Code Online (Sandbox Code Playgroud) 是否有任何可用的函数来处理大整数?
我找到了一个模块intarray,但是这个模块中的函数只能用于integer,而不是bigint。
我错过了从数组中删除项目的函数。类似于上述模块中“减号”运算符的实现:
int[] - int(从数组中删除匹配正确参数的条目)
我有一个 PostgreSQL 表,其中有一列包含字符串数组。该行有一些唯一的数组字符串,或者一些也有重复的字符串。如果存在,我想从每一行中删除重复的字符串。
我尝试了一些查询,但无法实现。
以下是表格:
veh_id | vehicle_types
--------+----------------------------------------
1 | {"byd_tang","volt","viper","laferrari"}
2 | {"volt","viper"}
3 | {"byd_tang","sonata","jaguarxf"}
4 | {"swift","teslax","mirai"}
5 | {"volt","viper"}
6 | {"viper","ferrariff","bmwi8","viper"}
7 | {"ferrariff","viper","viper","volt"}
Run Code Online (Sandbox Code Playgroud)
我期待以下输出:
veh_id | vehicle_types
--------+----------------------------------------
1 | {"byd_tang","volt","viper","laferrari"}
2 | {"volt","viper"}
3 | {"byd_tang","sonata","jaguarxf"}
4 | {"swift","teslax","mirai"}
5 | {"volt","viper"}
6 | {"viper","ferrariff","bmwi8"}
7 | {"ferrariff","viper","volt"}
Run Code Online (Sandbox Code Playgroud) 可以保证函数unnest()将按这些顺序返回值,它们是如何定位的?
也就是说,例如:
arr (INTEGER[])
---------------
{{3,5},{33,3}}
Run Code Online (Sandbox Code Playgroud)
这个查询:
SELECT unnest(arr) FROM "table"
总会回来的
3
5
33
3
Run Code Online (Sandbox Code Playgroud)
?
或者结果的排序可能与数组元素的排序不同?
在我的数据库中,我有一个表relations,其中有一列relation_ids包含用户 ID ( user_id)。它采用具有多个可能 ID 的数组形式,例如:
{111,112,156,4465}
Run Code Online (Sandbox Code Playgroud)
我还有另一个表,names其中包含有关用户的信息,例如user_id、first_name等last_name。
我想创建一个 SQL 查询来返回所有行relations和所有列,但将数组列附加relation_ids到替换 ID 的表first_name中。names
是否可以作为某种子查询?
Postgres 方法array_position(array, element)与 SQL 中的其他事物一样,是基于 1 的。例如:
SELECT array_position(array[4,5,6], 5) -- returns 2
Run Code Online (Sandbox Code Playgroud)
但是,我正在执行以下查询来从 pg_catalog 检索非唯一索引及其列:
SELECT array_position(array[4,5,6], 5) -- returns 2
Run Code Online (Sandbox Code Playgroud)
第四个选择indkey在数组中搜索列的ordinal_position,因此对于每一列,它都会获取其在索引中的位置。
有趣的是,第一列的位置为 0,所以我必须添加+ 1它以使其基于 1。
随后的CASE表达式使用完全相同的值作为检索 的第 n 个元素的索引indoption,奇怪的是,即使[]运算符也是基于 1 的,也能正常工作:
SELECT (array[4,5,6])[2] -- returns 5
Run Code Online (Sandbox Code Playgroud)
这怎么样?
我目前使用的是 PG 9.6。
postgresql ×12
arrays ×8
sql ×7
indexing ×2
sql-update ×2
ddl ×1
duplicates ×1
jsonb ×1
left-join ×1
routes ×1
unnest ×1
variations ×1