2008-10-03 9 views
17

En Oracle, dada una sencilla tabla de datos:Oracle mezclar constantes en una sola mesa

create table data (
    id  VARCHAR2(255), 
    key  VARCHAR2(255), 
    value VARCHAR2(511)); 

Supongamos que quiero "insertar o actualizar" un valor. Tengo algo como:

merge into data using dual on 
    (id='someid' and key='testKey') 
when matched then 
    update set value = 'someValue' 
when not matched then 
    insert (id, key, value) values ('someid', 'testKey', 'someValue'); 

¿Hay una mejor manera que esto? Este comando parece tener los siguientes inconvenientes:

  • las necesidades de cada literales a ser escrito dos veces (o añadido dos veces a través de parametrización)
  • El "usando dual" sintaxis parece hacky

Si esto es la mejor manera, ¿hay alguna forma de tener que establecer cada parámetro dos veces en JDBC?

+0

Si está utilizando 10g, "DUAL" es incluso menos pirata. antes de eso era una mesa real, en 10g no lo es. –

Respuesta

18

No considero que usar dual sea un hack. Para deshacerse de la unión/escribir dos veces, me gustaría hacer algo como:

merge into data 
using (
    select 
     'someid' id, 
     'testKey' key, 
     'someValue' value 
    from 
     dual 
) val on (
    data.id=val.id 
    and data.key=val.key 
) 
when matched then 
    update set data.value = val.value 
when not matched then 
    insert (id, key, value) values (val.id, val.key, val.value); 
-4

utilizar un procedimiento almacenado

4

Me ocultar la MERGE dentro de una API PL/SQL y luego llamar a que a través de JDBC:

data_pkg.merge_data ('someid', 'testKey', 'someValue'); 

Como alternativa a la mezcla, el API puede hacer:

begin 
    insert into data (...) values (...); 
exception 
    when dup_val_on_index then 
     update data 
     set ... 
     where ...; 
end; 
2

prefiero probar la actualización antes de la inserción de ahorrar tener que comprobar si hay una excepción.

update data set ...=... where ...=...; 

if sql%notfound then 

    insert into data (...) values (...); 

end if; 

Incluso ahora tenemos la declaración de combinación, todavía tienden a hacer cambios de una sola hilera de esta manera - sólo parece más una sintaxis más natural. Por supuesto, merge realmente sale a la luz cuando se trata de conjuntos de datos más grandes.

+1

Creo que tiene razón en que parece una sintaxis más natural, pero prefiero el enfoque de transacción única de la fusión: no hay posibilidad de que ocurra algo desafortunado entre la actualización y la inserción. –

+0

No puede pasar nada desafortunado entre la actualización y la inserción: esta es una vista de transacción consistente de Oracle. –

+0

¿Funciona esta sintaxis en oracle9i? –

0

Cuando la tabla de origen y la de destino son las mismas, debe usar DUAL.

Cuestiones relacionadas