2012-03-02 32 views
55

Sé que puede utilizar ON DUPLICATE KEY UPDATE para actualizar un cierto valor si hay un registro para esa tecla ya,¿Hay alguna manera de usar ON DUPLICATE KEY para actualizar todo lo que quería insertar?

Puedo hacer esto:

INSERT INTO `tableName` (`a`,`b`,`c`) VALUES (1, 2, 3) 
ON DUPLICATE KEY UPDATE `a`=1, `b`=2, `c`=3 

Pero, ¿cómo puedo hacer esto sin tener que escribir me sacar las columnas y los valores dos veces?

+0

http://stackoverflow.com/questions/294661/what-is-the-best-way-to-insert-into-and-update-one-row-table-in-mysql –

Respuesta

70

Unfortunately not.

Se puede llegar a mitad de camino al no tener que repetir el valor:

INSERT INTO `tableName` (`a`,`b`,`c`) VALUES (1,2,3) 
    ON DUPLICATE KEY UPDATE `a`=VALUES(`a`), `b`=VALUES(`b`), `c`=VALUES(`c`); 

Pero todavía tiene que enumerar las columnas.

+0

@Neal: Sus valores para insertar son complejos, ¿lo tomo? –

+0

:-(http://chat.stackoverflow.com/transcript/message/2819869#2819869 – Neal

+0

Parece que no funciona ^^^ – Neal

28

uso REPLACE INTO

El significado de REPLACE INTO es que si el nuevo disco presenta nuevos valores clave, a continuación, se inserta como nuevo registro.

si el nuevo registro tiene valores clave que responden a un registro ya existente, entonces la violación clave se ignora y el nuevo registro reemplazar el registro de pre-existente.

+5

Ah, eso podría ser mucho mejor. Vale la pena señalar que todos los campos no especificados en la consulta serán predeterminados, sin embargo, que obviamente difiere del comportamiento 'ON DUPLICATE KEY UPDATE'. –

+40

Nota: con 'REEMPLAZAR', si la clave del registro coincide con algo que ya existe, ** la fila anterior (s!) Se eliminará y la nueva se insertará **.Esto puede ser un gran problema si te metes con desencadenadores o restricciones de clave externa. – cHao

+2

Buen punto. Estás arriesgando algunas reacciones sustanciales en cadena, supongo. –

6

Si es útil, me hizo una consulta para evitar escribir a mano la última parte de la consulta "en duplicado", para las versiones> = 5.0:

SELECT GROUP_CONCAT(CONCAT(COLUMN_NAME,"=values(", COLUMN_NAME,")") SEPARATOR ", ") FROM INFORMATION_SCHEMA.COLUMNS WHERE TABLE_SCHEMA = 'database_name' AND TABLE_NAME = 'table_name'; 

y su salida es la siguiente:

a=values(a), b=values(b), c=values(c), d=values(d) 

en una tabla que tiene columnas a, B, C y D, por lo que puede anexar a la primera parte de la consulta:

INSERT INTO `tableName` (`a`,`b`,`c`, `d`) VALUES (1,2,3,4) ON DUPLICATE KEY UPDATE a=values(a), b=values(b), c=values(c), d=values(d) 

ACTUALIZACIÓN: Para una lista muy larga de columnas es posible que vea una salida truncada, puede utilizar esta declaración antes de la consulta anterior (gracias Uncle iroh):

SET SESSION group_concat_max_len = 1000000; 
+1

Me encanta esto. A veces necesito esto antes de su consulta muy útil. SET SESSION group_concat_max_len = 1000000; –

Cuestiones relacionadas