0

sales_staff_08 というテーブルと、名、姓、ユーザー名を 3 つの列として持っています。

ユーザー名は、名と姓を使用して連結されます。

重複する可能性があるためです。したがって、いくつかの数値を追加して回避したいと思います。

現在のテーブル

USERNAME   
---------- 
JOHSMITH1 
TOMNGUYE1
STEREDMO1
BOBJOHN1
CARJONES1
DANCREIG1
STEREDMO1
TOMNGUYE1

重複している RECORD を更新したいのですが、次のように表示されます。

USERNAME   
---------- 
JOHSMITH1
TOMNGUYE1
STEREDMO1
BOBJOHN1
CARJONES1
DANCREIG1
STEREDMO2
TOMNGUYE2

記録更新に初挑戦

 CREATE OR REPLACE PROCEDURE proc_concate_names IS 

 vc_username VARCHAR(25);
 v_number NUMBER (2) := 1;

 CURSOR cur_concate_username IS 
 SELECT firstname, surname, username FROM sales_staff_08; 

 BEGIN

    FOR rec_cur_concate IN cur_concate_username 

    LOOP

    vc_username := rec_cur_concate.firstname || rec_cur_concate.surname || v_number;

    UPDATE sales_staff_08 ss
    SET username = vc_username
    WHERE ss.username = rec_cur_concate.username;

 END LOOP; 

 END proc_concate_names;
 /
4

2 に答える 2

2

次の 1 つのコマンドで実行できます。

merge into sales_staff_08 d
using (select firstname ||surname || row_number() 
           over (partition by username order by firstname) un, rowid 
       from sales_staff_08 ) s
on (d.rowid = s.rowid)
when matched then update set d.username = s.un;

ここにsqlfiddleのデモがあります

@Plouf が述べたように、これは更新コマンドとしても実行できます。

update sales_staff_08 d
set d.username = (
  select un from (
    select firstname ||surname || row_number() 
            over (partition by firstname, surname order by firstname) un 
     from sales_staff_08
  ) s
  where s.rowid = d.rowid
)

ここに別のsqlfiddleがあります

于 2013-02-11T06:53:52.363 に答える
2

ABcade の回答の方が信頼性が高いです。まず、何百万もの行がある場合、マージと更新はより高速に動作します。最初のケースでは、操作にplsqlエンジンとsqlエンジンの両方を使用しているためです。これは、plsql エンジンの各ループで、SQL エンジンを呼び出すことを意味します。2 番目のケースでは、より高速な完全に独立した SQL エンジンを使用します。

于 2013-02-11T09:47:42.647 に答える