Je veux remplir une colonne de table avec un nombre entier en cours d'exécution, je pense donc à utiliser ROWNUM. Cependant, je dois le remplir en fonction de l'ordre des autres colonnes, quelque chose comme ORDER BY column1, column2
. Ce n'est malheureusement pas possible car Oracle n'accepte pas la déclaration suivante:
UPDATE table_a SET sequence_column = rownum ORDER BY column1, column2;
Ni la déclaration suivante (une tentative d'utilisation de la clause WITH):
WITH tmp AS (SELECT * FROM table_a ORDER BY column1, column2)
UPDATE tmp SET sequence_column = rownum;
Alors, comment puis-je le faire en utilisant une instruction SQL et sans recourir à la méthode d'itération du curseur en PL/SQL?
Cela devrait fonctionner (fonctionne pour moi)
update table_a outer
set sequence_column = (
select rnum from (
-- evaluate row_number() for all rows ordered by your columns
-- BEFORE updating those values into table_a
select id, row_number() over (order by column1, column2) rnum
from table_a) inner
-- join on the primary key to be sure you'll only get one value
-- for rnum
where inner.id = outer.id);
OU vous utilisez l'instruction MERGE
. Quelque chose comme ça.
merge into table_a u
using (
select id, row_number() over (order by column1, column2) rnum
from table_a
) s
on (u.id = s.id)
when matched then update set u.sequence_column = s.rnum
UPDATE table_a
SET sequence_column = (select rn
from (
select rowid,
row_number() over (order by col1, col2)
from table_a
) x
where x.rowid = table_a.rowid)
Mais cela ne sera pas très rapide et comme l'a souligné Damien, vous devez réexécuter cette instruction chaque fois que vous modifiez des données dans cette table.
Créez d'abord une séquence:
CREATE SEQUENCE SEQ_SLNO
START WITH 1
MAXVALUE 999999999999999999999999999
MINVALUE 1
NOCYCLE
NOCACHE
NOORDER;
après cela, mettez à jour la table en utilisant la séquence:
UPDATE table_name
SET colun_name = SEQ_SLNO.NEXTVAL;
Une petite correction vient d'ajouter AS RN:
UPDATE table_a
SET sequence_column = (select rn
from (
select rowid,
row_number() over (order by col1, col2) AS RN
from table_a
) x
where x.rowid = table_a.rowid)