PgSql 插入多个 regexp_split_to_table 的多条记录
PgSql Insert multiple records with multiple regexp_split_to_table
我有一个 table 列 [FileId, FileName, FileUrl]。
我在 INSERT 存储过程的输入参数中将 FileName 和 FileUrl 作为逗号分隔字符串 (v_FileName, v_FileUrl) 获取,并且 FileId 是自动递增的。
如果我按如下方式使用 regexp_split_to_table 一次,则 FileName 的记录插入成功:
INSERT INTO MYTABLE
SELECT nextval('mytable_fileid_seq'),
,regexp_split_to_table
,'testurl'
FROM regexp_split_to_table(v_FileName, E',')
这成功地为 v_FileName 参数中的所有文件名插入了行,并像上面的测试脚本一样为 fileurl 设置了 'testurl'。
我的问题是,是否也可以在这样的单行中使用 regexp_split_to_table 为 v_FileUrl 参数设置 FileUrl?我试过了,但它给出了 "regexp_split_to_table is used more than once" 类的错误。 (可能是我使用不当。)
或者建议我使用此类输入参数插入记录的任何其他方法。
提前致谢。
如果您需要将逗号分隔的字符串存储到多行中。您可以查看以下代码;
逗号分隔的字符串 - “1,2,3,4,5,6”
create table schema_name.table_name(id int);
insert into schema_name.table_name
(
SELECT CAST(regexp_split_to_table('1,2,3,4,5,6', ',') AS INTEGER) AS id
) ;
select * from schema_name.table_name
一种选择是使用 unnest
和 regexp_split_to_array
:
SELECT * FROM unnest(
regexp_split_to_array('a,b,c',','),
regexp_split_to_array('1,2,3',',')
);
结果:
unnest | unnest
--------+--------
a | 1
b | 2
c | 3
所以在你的情况下:
INSERT INTO mytable (FileName, FileUrl)
SELECT *
FROM unnest(
regexp_split_to_array(v_FileName,','),
regexp_split_to_array(v_FileUrl,',')
);
(我假设您的 FileId 使用该序列具有正确的 default
值)。
下面的解决方案完全符合我的期望。提供扩展 MYTABLE 的解决方案,因为我的实际 table 包含更多列。另外,这对其他有相同要求的人会更有帮助。
列:
FileId, StoryId, FileName, FileHref, InsertDate
使用示例值插入存储的过程输入参数:
v_StoryId = 5678,
v_FileName = 'File_1.jpg,File_2.pdf,File_3.jpg,File_4.pdf'
v_FileHref = 'www.abc.com/File_1.jpg,www.abc.com/File_2.pdf,www.abc.com/File_3.jpg,www.abc.com/File_4.pdf'
有效的代码块:
INSERT INTO MYTABLE
(SELECT NextVal('mytable_fileid_seq')
,v_StoryId
,FileName.regexp_split_to_table
,FileHref.regexp_split_to_table
,LOCALTIMESTAMP
FROM ( select row_number() over () as idx,
i as regexp_split_to_table
from UNNEST(STRING_TO_ARRAY(v_FileName,',')) i
)as FileName
JOIN ( select row_number() over () as idx,
i as regexp_split_to_table
from UNNEST(string_to_array(v_FileHref,',')) i
)as FileHref
ON FileName.idx = FileHref.idx
);
结果:
FileId | StoryId | FileName |FileHref |InsertDate
--------------------------------------------------------------------------------------------
23 | 1234 |File_1.jpg |www.abc.com/File_1.jpg | 2016-12-14 12:11:54.374933
--------------------------------------------------------------------------------------------
24 | 1234 |File_2.pdf |www.abc.com/File_2.pdf | 2016-12-14 12:11:54.374933
--------------------------------------------------------------------------------------------
25 | 1234 |File_3.jpg |www.abc.com/File_3.jpg | 2016-12-14 12:11:54.374933
--------------------------------------------------------------------------------------------
26 | 1234 |File_4.pdf |www.abc.com/File_4.pdf | 2016-12-14 12:11:54.374933
但是,目前使用 regexp_split_to_table() 和 unnest() 感觉很可疑,但就我而言,逗号分隔值可能不会增加到 30,因此该代码段应该没问题。目前我是 pgsql 的新手,但如果有人有 better/neat 解决方案,那么当然不胜感激。
感谢@jcaron 指明了解决方案的方向。
我有一个 table 列 [FileId, FileName, FileUrl]。 我在 INSERT 存储过程的输入参数中将 FileName 和 FileUrl 作为逗号分隔字符串 (v_FileName, v_FileUrl) 获取,并且 FileId 是自动递增的。 如果我按如下方式使用 regexp_split_to_table 一次,则 FileName 的记录插入成功:
INSERT INTO MYTABLE
SELECT nextval('mytable_fileid_seq'),
,regexp_split_to_table
,'testurl'
FROM regexp_split_to_table(v_FileName, E',')
这成功地为 v_FileName 参数中的所有文件名插入了行,并像上面的测试脚本一样为 fileurl 设置了 'testurl'。
我的问题是,是否也可以在这样的单行中使用 regexp_split_to_table 为 v_FileUrl 参数设置 FileUrl?我试过了,但它给出了 "regexp_split_to_table is used more than once" 类的错误。 (可能是我使用不当。)
或者建议我使用此类输入参数插入记录的任何其他方法。
提前致谢。
如果您需要将逗号分隔的字符串存储到多行中。您可以查看以下代码;
逗号分隔的字符串 - “1,2,3,4,5,6”
create table schema_name.table_name(id int);
insert into schema_name.table_name
(
SELECT CAST(regexp_split_to_table('1,2,3,4,5,6', ',') AS INTEGER) AS id
) ;
select * from schema_name.table_name
一种选择是使用 unnest
和 regexp_split_to_array
:
SELECT * FROM unnest(
regexp_split_to_array('a,b,c',','),
regexp_split_to_array('1,2,3',',')
);
结果:
unnest | unnest
--------+--------
a | 1
b | 2
c | 3
所以在你的情况下:
INSERT INTO mytable (FileName, FileUrl)
SELECT *
FROM unnest(
regexp_split_to_array(v_FileName,','),
regexp_split_to_array(v_FileUrl,',')
);
(我假设您的 FileId 使用该序列具有正确的 default
值)。
下面的解决方案完全符合我的期望。提供扩展 MYTABLE 的解决方案,因为我的实际 table 包含更多列。另外,这对其他有相同要求的人会更有帮助。
列:
FileId, StoryId, FileName, FileHref, InsertDate
使用示例值插入存储的过程输入参数:
v_StoryId = 5678,
v_FileName = 'File_1.jpg,File_2.pdf,File_3.jpg,File_4.pdf'
v_FileHref = 'www.abc.com/File_1.jpg,www.abc.com/File_2.pdf,www.abc.com/File_3.jpg,www.abc.com/File_4.pdf'
有效的代码块:
INSERT INTO MYTABLE
(SELECT NextVal('mytable_fileid_seq')
,v_StoryId
,FileName.regexp_split_to_table
,FileHref.regexp_split_to_table
,LOCALTIMESTAMP
FROM ( select row_number() over () as idx,
i as regexp_split_to_table
from UNNEST(STRING_TO_ARRAY(v_FileName,',')) i
)as FileName
JOIN ( select row_number() over () as idx,
i as regexp_split_to_table
from UNNEST(string_to_array(v_FileHref,',')) i
)as FileHref
ON FileName.idx = FileHref.idx
);
结果:
FileId | StoryId | FileName |FileHref |InsertDate
--------------------------------------------------------------------------------------------
23 | 1234 |File_1.jpg |www.abc.com/File_1.jpg | 2016-12-14 12:11:54.374933
--------------------------------------------------------------------------------------------
24 | 1234 |File_2.pdf |www.abc.com/File_2.pdf | 2016-12-14 12:11:54.374933
--------------------------------------------------------------------------------------------
25 | 1234 |File_3.jpg |www.abc.com/File_3.jpg | 2016-12-14 12:11:54.374933
--------------------------------------------------------------------------------------------
26 | 1234 |File_4.pdf |www.abc.com/File_4.pdf | 2016-12-14 12:11:54.374933
但是,目前使用 regexp_split_to_table() 和 unnest() 感觉很可疑,但就我而言,逗号分隔值可能不会增加到 30,因此该代码段应该没问题。目前我是 pgsql 的新手,但如果有人有 better/neat 解决方案,那么当然不胜感激。
感谢@jcaron 指明了解决方案的方向。