Przepisanie rekordów do innej tabeli z pominięciem istniejących

0

Siemanko, tak jak w temacie mam dwie tabele o identycznej strukturze, chciałbym przepisać rekordy z pierwszej tabeli do drugiej, które nie są jeszcze w drugiej, przykład:
W oczekiwanym wyniku w tabeli drugiej został jeden rekord jeszcze w niej nie istniejący, a rekord już istniejący pominięty

tabela 1:
| data   | id  | wartość   |
|2019-1-2| 2   |     15    | 
|2019-1-3|  1  |      15   | 

tabela 2:
|data     | id | wartość   |
|2019-1-2 | 1  |     15    | 
|2019-1-2 | 2  |     15    | 

Oczekiwany wynik drugiej tabeli:
| data    | id | wartość |
|2019-1-2 | 1  |     15  |
|2019-1-2 | 2  |     15  | 
|2019-1-3 | 1  |     15  | 
0

Wystarczy union

select * from tab1
union
select * from tab2
0

Można za pomocą INSERT / SELECT.

Selecta moża różnie realizować, np. za pomocą operatorów na zbiorach (niektóre silniki nazywają ten operator MINUS, inne EXCEPT), czy EXISTS:

insert into a 
(select * from b minus select * from a);
insert into a
  select * from b where not exists (select 1 from a where b.id=a.id); 
0
yarel napisał(a):

Można za pomocą INSERT / SELECT.

Selecta moża różnie realizować, np. za pomocą operatorów na zbiorach (niektóre silniki nazywają ten operator MINUS, inne EXCEPT), czy EXISTS:

insert into a 
(select * from b minus select * from a);
insert into a
  select * from b where not exists (select 1 from a where b.id=a.id); 

No właśnie chciałem to zrobić tak jak w Twoim drugim kodzie, tyle, że nie mam tutaj żadnego klucza ani nic, gdyż tabela z której importuję się ciągle zmienia, a dane, które do niej lecą są z różnych źródeł, więc ciężko byłoby napisać jakiś kod generujący klucz.

Aktualnie mam to zrobione tak:

INSERT INTO history (id, pomiar1, pomiar2, lat)
SELECT p.id,p.pomiar1,p.pomiar2,s.lat
 FROM pomiary p inner join SN s on p.id=s.id 
WHERE NOT EXISTS(SELECT p2.*,s2.* from pomiary p2 inner join SN s2 on p2.id=s2.id where p2.pomiar1=p.pomiar1 and p2.pomiar2=p.pomiar2 and p.id=p2.id and s2.lat=s.lat and s.id=s2.id)

I o ile w zapytaniu nie ma błędu o tyle niczego ono nie robi (0 rows affected), nie wspomniałem co prawda o tym, że dane łączone są z dwóch tabel i wrzucane w jedną, ale to chyba nie jest duża zmiana

0

LEFT JOIN z NULLem

0

analizując samego selecta w insercie

SELECT p.id,
       p.pomiar1,
       p.pomiar2,
       s.lat
FROM pomiary p
     INNER JOIN SN s ON p.id = s.id
WHERE NOT EXISTS
(
    SELECT p2.*,
           s.*
    FROM pomiary p2
         INNER JOIN SN s2 ON p2.id = s2.id
    WHERE p2.pomiar1 = p.pomiar1
          AND p2.pomiar2 = p.pomiar2
          AND p.id = p2.id
          AND s2.lat = s.lat
          AND s.id = s2.id
);

To pobierasz dane:

SELECT p.id,
       p.pomiar1,
       p.pomiar2,
       s.lat
FROM pomiary p
     INNER JOIN SN s ON p.id = s.id

i chcesz wziąć tylko rekordy ktorych nie ma w tym podzapytaniu:


    SELECT p2.*,
           s.*
    FROM pomiary p2
         INNER JOIN SN s2 ON p2.id = s2.id

Powiedz mi, co ma być rózne skoro pobierasz 2 takie same zestawy?

Jak rozumiem chcesz uzupełnić tabele historii, więc coś w ten deseń:

SELECT p.id,
       p.pomiar1,
       p.pomiar2,
       s.lat
FROM pomiary p
     INNER JOIN SN s ON p.id = s.id
WHERE NOT EXISTS
(
    SELECT 1
    FROM  history h
    WHERE h.pomiar1 = p.pomiar1
          AND h.pomiar2 = p.pomiar2
          AND h.id = p.id
          AND h.lat = s.lat
);
0
Panczo napisał(a):

analizując samego selecta w insercie

SELECT p.id,
       p.pomiar1,
       p.pomiar2,
       s.lat
FROM pomiary p
     INNER JOIN SN s ON p.id = s.id
WHERE NOT EXISTS
(
    SELECT p2.*,
           s.*
    FROM pomiary p2
         INNER JOIN SN s2 ON p2.id = s2.id
    WHERE p2.pomiar1 = p.pomiar1
          AND p2.pomiar2 = p.pomiar2
          AND p.id = p2.id
          AND s2.lat = s.lat
          AND s.id = s2.id
);

To pobierasz dane:

SELECT p.id,
       p.pomiar1,
       p.pomiar2,
       s.lat
FROM pomiary p
     INNER JOIN SN s ON p.id = s.id

i chcesz wziąć tylko rekordy ktorych nie ma w tym podzapytaniu:


    SELECT p2.*,
           s.*
    FROM pomiary p2
         INNER JOIN SN s2 ON p2.id = s2.id

Powiedz mi, co ma być rózne skoro pobierasz 2 takie same zestawy?

Jak rozumiem chcesz uzupełnić tabele historii, więc coś w ten deseń:

SELECT p.id,
       p.pomiar1,
       p.pomiar2,
       s.lat
FROM pomiary p
     INNER JOIN SN s ON p.id = s.id
WHERE NOT EXISTS
(
    SELECT 1
    FROM  history h
    WHERE h.pomiar1 = p.pomiar1
          AND h.pomiar2 = p.pomiar2
          AND h.id = p.id
          AND h.lat = s.lat
);

Już udało mi się osiągnąć efekt:

INSERT INTO history (id, pomiar1, pomiar2, lat)
SELECT p.id,p.pomiar1,p.pomiar2,s.lat
FROM pomiary p inner join SN s on p.id=s.id 
WHERE NOT EXISTS(SELECT h.id, h.pomiar1,h.pomiar2,h.lat from history h  where h.pomiar1=p.pomiar1 and h.pomiar2=p.pomiar2 and p.id=h.id and h.lat=s.lat and s.id=h.id)
0

Ten warunek w podzapytaniu: and s.id=h.id nie jest Ci potrzebny skoro p.id=s.id => s.id=h.id bo wczesniej w WHERE masz: p.id=h.id

1 użytkowników online, w tym zalogowanych: 0, gości: 1