2009-04-07 2 views
79

Come posso unire due tabelle MySQL che hanno la stessa struttura?Come posso unire due tabelle MySQL?

Le chiavi primarie delle due tabelle si scontreranno, quindi ne ho tenuto conto.

+6

Quando si dice che i PK potrebbero essere incompatibili, vuoi dire che ci potrebbe essere righe duplicate e non si desidera li copiati, o che è necessario assegnare un nuovo PK a uno di loro perché sono file davvero diversi pur avendo lo stesso PK?(ancora un altro motivo per usare le chiavi primarie naturali) –

risposta

105

Potete anche provare:

INSERT IGNORE 
    INTO table_1 
SELECT * 
    FROM table_2 
    ; 

che permette le righe in Table_1 a sostituire quelli in table_2 che hanno una chiave primaria corrispondente, mentre ancora l'inserimento di righe con nuove chiavi primarie.

alternativa,

REPLACE 
    INTO table_1 
SELECT * 
    FROM table_2 
     ; 

aggiornerà le righe già Table_1 con riga corrispondente da table_2, mentre l'inserimento di righe con nuove chiavi primarie.

+2

potrebbe essere DA molti tavoli? – SaidbakR

+1

In realtà, [REPLACE] (http://code.openark.org/blog/mysql/replace-into-think-twice) righe esistenti (cancella + inserisci), non aggiorna. –

13

Se è necessario farlo manualmente, una volta:

In primo luogo, si fondono in una tabella temporanea, con qualcosa come:

create table MERGED as select * from table 1 UNION select * from table 2 

Poi, identificare i vincoli di chiave primaria con qualcosa di simile

SELECT COUNT(*), PK from MERGED GROUP BY PK HAVING COUNT(*) > 1 

Dove PK è il campo chiave primaria ...

Risolvi il DUPL icates.

Rinominare la tabella.

[Modificato - staffe rimosse nella query UNION, che stava causando l'errore nel commento qui sotto]

+0

quando provo questo ho ricevuto questo errore, "ERRORE 1064 (42000): Hai un errore nella sintassi SQL, controlla il manuale che corrisponde alla versione del tuo server MySQL per la sintassi corretta da usare vicino a "UNION select * from actor") alla riga ", perché? – jcho360

19
INSERT 
INTO first_table f 
SELECT * 
FROM second_table s 
ON DUPLICATE KEY 
UPDATE 
     s.column1 = DO_WHAT_EVER_MUST_BE_DONE_ON_KEY_CLASH(f.column1) 
+1

Grazie per la buona idea. Il precedente cmd mi dà comunque un errore di sintassi. Ma questo funziona per me: INSERT INTO prima_tabella SELECT * FROM second_table ON DUPLICATE KEY UPDATE second_table.column1 = DO_WHAT_EVER_MUST_BE_DONE_ON_KEY_CLASH (first_table.column1) – Tapper

+0

Proprio come @Tapper, non ho potuto ottenere per assegnare un alias al primo tavolo. Avrei comunque ottenuto "Errore di sintassi, inaspettato IDENT_QUOTED" - tramite MySQL Workbench. – blo0p3r

35

Dipende dalla semantica della chiave primaria. Se è solo AutoIncrement, quindi usare qualcosa come:

insert into table1 (all columns except pk) 
select all_columns_except_pk 
from table2; 

Se PK significa qualcosa, è necessario trovare un modo per determinare quale record dovrebbe avere la priorità. È possibile creare una query di selezione per trovare prima i duplicati (vedere answer by cpitis). Quindi elimina quelli che non vuoi conservare e usa l'inserto sopra per aggiungere i record che rimangono.

0

Si potrebbe scrivere uno script per aggiornare il FK per voi .. controllare questo blog: http://multunus.com/2011/03/how-to-easily-merge-two-identical-mysql-databases/

Hanno uno script intelligente per utilizzare le tabelle INFORMATION_SCHEMA per ottenere l ' "ID" colonne:

SET @db:='id_new'; 

select @max_id:=max(AUTO_INCREMENT) from information_schema.tables; 

select concat('update ',table_name,' set ', column_name,' = ',column_name,'+',@max_id,' ; ') from information_schema.columns where [email protected] and column_name like '%id' into outfile 'update_ids.sql'; 

use id_new 
source update_ids.sql; 
5

Non così complicato come sembra ... Basta lasciare la chiave primaria duplicata fuori dalla query .... questo funziona per me!

INSERT INTO 
    Content(
    `status`, 
    content_category, 
    content_type, 
    content_id, 
    user_id, 
    title, 
    description, 
    content_file, 
    content_url, 
    tags, 
    create_date, 
    edit_date, 
    runs 
) 
SELECT `status`, 
    content_category, 
    content_type, 
    content_id, 
    user_id, 
    title, 
    description, 
    content_file, 
    content_url, 
    tags, 
    create_date, 
    edit_date, 
    runs 
FROM 
    Content_Images