Oracle 12c 用相同的数据更新多行

Posted

技术标签:

【中文标题】Oracle 12c 用相同的数据更新多行【英文标题】:Oracle 12c updating multiple rows with the same data 【发布时间】:2020-06-30 21:41:09 【问题描述】:

我正在尝试编写一个脚本来提取字符串中所有不同的“单词”并将它们保存在另一个字段中。我已经获得了在 Oracle 19c 中工作的过程(尽管欢迎任何建议)但是当我在 12c 中运行脚本时,第一条记录是正确的,但是以下所有记录都有相同的数据,我不确定我是什么做错了。

谢谢!

drop table temp purge;
create table temp (A CHAR(1), S1 varchar(32), S2 varchar(32));
commit;

insert into temp (A,S1)
select 'A', '1 2 3 4 1 2 3 4 1 2 3 4' from dual;
commit;
insert into temp (A,s1)
select 'B', '6 7 8 9 6 7 8 9 6 7 8 9 6 7 8 9' from dual;
commit;
insert into temp (A,s1)
select 'C', 'A B C D A B C D' from dual;
commit;

select * from temp;

UPDATE temp set (S2) = (
    SELECT LISTAGG(str, ' ') WITHIN GROUP (ORDER BY str) str
    FROM (
        SELECT DISTINCT REGEXP_SUBSTR(S1, '[^ ]+', 1, LEVEL) AS str FROM dual
        CONNECT BY REGEXP_SUBSTR(S1, '[^ ]+', 1, LEVEL) IS NOT NULL
    )
);


select * from temp;

输出:

A S1                               S2
- -------------------------------- --------------------------------
A 1 2 3 4 1 2 3 4 1 2 3 4
B 6 7 8 9 6 7 8 9 6 7 8 9 6 7 8 9
C A B C D A B C D


3 rows updated.


A S1                               S2
- -------------------------------- --------------------------------
A 1 2 3 4 1 2 3 4 1 2 3 4          1 2 3 4
B 6 7 8 9 6 7 8 9 6 7 8 9 6 7 8 9  1 2 3 4
C A B C D A B C D                  1 2 3 4

预期:

A S1                               S2
- -------------------------------- --------------------------------
A 1 2 3 4 1 2 3 4 1 2 3 4          1 2 3 4
B 6 7 8 9 6 7 8 9 6 7 8 9 6 7 8 9  6 7 8 9
C A B C D A B C D                  A B C D

【问题讨论】:

【参考方案1】:

我不知道问题是什么,但这里有一个替代解决方案,可以避免使用 REGEXP 造成的 CPU 损失:

update temp set s2 =
xmlcast(
  xmlquery(
    'string-join(distinct-values(tokenize($X, " ")), " ")'
    passing s1 as X returning content
  )
  as varchar2(64)
);

【讨论】:

【参考方案2】:

请尝试以下方法,它应该可以工作 -

update (
select temp.*
      ,(SELECT LISTAGG(str, ' ') WITHIN GROUP (ORDER BY str) str
          FROM (
                SELECT DISTINCT REGEXP_SUBSTR(S1, '[^ ]+', 1, LEVEL) AS str FROM dual
                CONNECT BY REGEXP_SUBSTR(S1, '[^ ]+', 1, LEVEL) IS NOT NULL
               )
        ) result
  from temp
)
set S2 = result

这里的关键是确保为每一行计算 S2。

【讨论】:

以上是关于Oracle 12c 用相同的数据更新多行的主要内容,如果未能解决你的问题,请参考以下文章

oracle 两行及多行关键字相同数据并为一条数据

oracle中如何把表中具有相同值列的多行数据合并成一行

如何在 oracle 12c 中使用多个数据更新单个列

如何在mysql中更新具有相同值的多行[关闭]

oracle11g安装完怎么使用

Oracle12c Data Guard搭建手册