Here are two tables. I want to UPDATE (NOT to SELECT) the first table based on the info from both tables.
The first table named somecities
:
Name - State - Country - Info1 - Info2
Orlando - FL - US - 123 -AAA
Hrodna - HV - BY - 890 -BBB
The second table named allcities
:
Name - State - Country - Info1
Orlando - FL - US - 123
Orlando - KY - US - 456
Orlando - WV - US - 789
Orlando - SW - SA - 333
Hrodna - HV - BY - 890
Minsk - MV - BY - 199
Any pair of (Name, State, Country) from somecities
table is in the allcities
table, if it matters. So, the allcities
table is bigger.
I want to modify somecities
this way:
1)take the first row, take Orlando
. It is met 4 times in allcities
. So, make 4 strings of Orlando instead of one (add 3 rows to somecities).
2) Take the next city (the second and the last one) - Hrodna
. Hrodna
is met only one time in allcities so we do not add any rows (add zero rows) to somecities
.
3) Do it for each row in somecities
.
The result of the query is the updated somecities
:
Name - State - Country - Info1 - Info2
Orlando - FL - US - 123 - AAA
Orlando - KY - US - 456 - AAA
Orlando - WV - US - 789 - AAA
Orlando - SW - SA - 333 - AAA
Hrodna - HV - BY - 890 - BBB
PS As you can see, the values in the Info2 are taken from Info2 for the same city.
Can it be done in one query? Two queries as an answer will be accepted as well.
Did I explain it clear?
Thank you.
You need an INSERT query, you could use something like this:
INSERT INTO somecities
SELECT a.*, si.Info2
FROM
allcities a LEFT JOIN somecities s
ON a.Name=s.Name AND a.State=s.State AND a.Country=s.Country
INNER JOIN (SELECT DISTINCT Name, Info2
FROM somecities) si
ON a.Name=si.Name
WHERE
s.Name IS NULL
Please see fiddle here .
This will insert ALL rows from allcities that are not present in somecities (or that have the same name but a different state or country) because I'm using a LEFT JOIN with a WHERE s.Name IS NULL.
Then I'm selection the name of the cities and the Info2 column that are present in somecities, and I'm doing an INNER JOIN on just the Name, in order to return only the rows that are present in somecities at least once.
You can use NOT EXISTS
to test for records that are not already in your table, then do a quick join to get the info2 from the existing records:
INSERT INTO somecities (Name,State,Country,Info1, Info2)
SELECT data.Name,data.State,data.Country,data.Info1,inf.Info2
FROM (
SELECT *
FROM allcities a
WHERE NOT EXISTS (SELECT *
FROM somecities s
WHERE s.name = a.name
AND s.state = a.state
AND s.country = a.country
AND s.info1 = a.info1
)
) data
INNER JOIN (SELECT DISTINCT Name, Info2 FROM somecities) inf
ON data.name = inf.name;
I personally find it easier to read EXISTS
and NOT EXISTS
rather than lots of joins but it's a personal preference, take your pick.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.