Necesito actualizar una consulta para que compruebe que una entrada duplicada no exista antes de la inserción. En MySQL puedo usar INSERT IGNORE para que, si se encuentra un registro duplicado, se salte la inserción, pero parece que no puedo encontrar una opción equivalente para Oracle. ¿Alguna sugerencia?Oracle Equivalente a MySQL INSERT IGNORE?
Respuesta
Echa un vistazo a la instrucción MERGE. Esto debería hacer lo que quieras; es la cláusula WHEN NOT MATCHED
lo que hará esto.
hacer a la falta de Oracle de apoyo para una auténtica VALORES() cláusula de la sintaxis para un único registro con valores fijos es bastante torpe sin embargo:
MERGE INTO your_table yt
USING (
SELECT 42 as the_pk_value,
'some_value' as some_column
FROM dual
) t on (yt.pk = t.the_pke_value)
WHEN NOT MATCHED THEN
INSERT (pk, the_column)
VALUES (t.the_pk_value, t.some_column);
Un enfoque diferente (si está por ejemplo haciendo de carga a granel de una tabla diferente) es usar el recurso "Error logging" de Oracle. La declaración podría tener este aspecto:
INSERT INTO your_table (col1, col2, col3)
SELECT c1, c2, c3
FROM staging_table
LOG ERRORS INTO errlog ('some comment') REJECT LIMIT UNLIMITED;
Posteriormente todas las filas que han lanzado un error están disponibles en la tabla errlog
. Debe crear esa tabla errlog
(o el nombre que elija) manualmente antes de ejecutar la inserción usando DBMS_ERRLOG.CREATE_ERROR_LOG
.
Consulte el manual para más detalles
No creo que no hay más que para ahorrar tiempo se puede intentar la inserción e ignorar lo inevitable de error:
begin
insert into table_a(col1, col2, col3)
values (1, 2, 3);
exception when dup_val_on_index then
null;
end;
/
Esto sólo ignorar excepciones planteadas específicamente por clave primaria duplicado o restricciones de claves únicas; todo lo demás se levantará como normal.
Si no desea hacer esto, primero tiene que seleccionar de la tabla, que no es tan eficiente.
¿Qué hay de la simple adición de un índice con lo que los campos que necesita para comprobar si hay duplicados y decir que debe ser único? Guarda una verificación de lectura.
Porque fallará el inserto si hay duplicados, cuando realmente es posible que solo quiera omitirlos. –
Si estás en 11g se puede utilizar la sugerencia IGNORE_ROW_ON_DUPKEY_INDEX:
SQL> create table my_table(a number, constraint my_table_pk primary key (a));
Table created.
SQL> insert /*+ ignore_row_on_dupkey_index(my_table, my_table_pk) */
2 into my_table
3 select 1 from dual
4 union all
5 select 1 from dual;
1 row created.
¡gracias esto funcionó! pero parece ser una solución no estándar ... como si alguien recordara alguna vez esta notación. –
@SonicSoul Tienes razón, es una forma inusual de codificar. El manual incluso señala que las sugerencias normalmente no tienen un efecto semántico. Como todos los consejos, este debe ser usado con cuidado. Por ejemplo, si la sugerencia fue mal escrita, no habría error de tiempo de compilación, la característica simplemente no funcionaría silenciosamente. –
Sí, recientemente llegué al desarrollo de Oracle y estoy bastante desconcertado por la cantidad de estos trucos para lograr lo que solía pensar que eran cosas simples con sql :) –
Una solución sencilla
insert into t1
select from t2
where not exists
(select 1 from t1 where t1.id= t2.id)
Otra variante
Insert into my_table (student_id, group_id)
select distinct p.studentid, g.groupid
from person p, group g
where NOT EXISTS (select 1
from my_table a
where a.student_id = p.studentid
and a.group_id = g.groupid)
o que podría hacer
Insert into my_table (student_id, group_id)
select distinct p.studentid, g.groupid
from person p, group g
MINUS
select student_id, group_id
from my_table
Ésta no es la mía, pero llegó en muy práctico cuando se utiliza sqlloader:
crear una vista que apunta a la tabla:
CREATE OR REPLACE VIEW test_view AS SELECT * FROM test_tab
crear el gatillo:
CREATE OR REPLACE TRIGGER test_trig INSTEAD OF INSERT ON test_view FOR EACH ROW BEGIN INSERT INTO test_tab VALUES (:NEW.id, :NEW.name); EXCEPTION WHEN DUP_VAL_ON_INDEX THEN NULL; END test_trig;
y en el archivo ctl, inserte en la vista en su lugar:
OPTIONS(ERRORS=0) LOAD DATA INFILE 'file_with_duplicates.csv' INTO TABLE test_view FIELDS TERMINATED BY ',' (id, field1)
- 1. MySQL equivalente de SEQUENCE.NEXTVAL de Oracle
- 2. Equivalente al RowID de Oracle en MySQL
- 3. Equivalente a \ G de MySQL en SQL * Plus de Oracle
- 4. mysql función para proporcionar equivalente a Oracle NVL
- 5. SQLAlchemy - INSERT O REPLACE equivalente
- 6. MySQL INSERT o SELECCIONAR
- 7. MYSQL INSERT SELECCIONAR problema
- 8. Equivalente de Oracle del tipo de texto de MySQL
- 9. ¿Hay algún equivalente para paquetes (Oracle) en MySQL?
- 10. ¿Hay MySQL equivalente al TIMESTAMP de Oracle CON HUSO HORARIO?
- 11. Migrar de Oracle a MySQL
- 12. equivalente de Oracle de la actualización de MySQL ignore
- 13. ¿Tiene mysql el equivalente de las "funciones analíticas" de Oracle?
- 14. MySQL equivalente de la función DECODE en Oracle
- 15. MySql INSERT contra PHP file_put_contents
- 16. Oracle equivalente a DISTINCT ON de Postgres?
- 17. Oracle equivalente a SQL Server DATEPART
- 18. Oracle es equivalente a java System.currentTimeMillis()?
- 19. Oracle equivalente a SQL Server/Sybase DateDiff
- 20. comando insert negado en MySQL
- 21. MySQL - EN llave duplicada INSERT
- 22. ¿Existe un Oracle equivalente a OUTPUT INSERTED de SQL Server. *?
- 23. Oracle 'printf' equivalente
- 24. MySQL INSERT INTO table VALUES ... vs INSERT INTO table SET
- 25. Use "LIMIT" en MySQL "INSERT"?
- 26. Alemán diéresis en MYSQL INSERT
- 27. INSERT INTO con subconsulta MySQL
- 28. LOAD DATA INFILE equivalente en Oracle
- 29. Hibernate con MySQL: Auto-Generate Id: Equivalente de secuencia (Oracle) en MySQL
- 30. SQLite equivalente para Oracle ROWNUM?
errores de registro todavía podrá lanzar una excepción en violaciónes de clave única o primaria, a menos que las cosas han cambiado desde: http://asktom.oracle.com/pls/apex/f?p=100:11: 0 :::: P11_QUESTION_ID: 1500471500346067777 –
@ShannonSeverance: Funciona para 'INSERT's, que es lo que Bad Programmer está pidiendo. Pero gracias por el enlace no sabía que no funciona para las actualizaciones en el PK (solo lo uso para inserciones) –
¿No debería reemplazarse la palabra clave 'FROM' por la palabra clave' USING'? Eche un vistazo a http://stackoverflow.com/questions/16414747/oracle-equivalent-of-insert-ignore si es necesario. – Wis