我正在尝试从另一个表(all_data)向一个表(some_data)添加一个列;最初,id_a和id_b将是一个足够的外键,我将使用它们来唯一地标识表all_info中的值,以带来表some_data。但是,某些地方 some_data中id_b的某些已损坏。因此,我想在some_data中添加一个列,当id_a和id_b存在完全匹配时仍然使用all_info中的值,或者,如果id_a和id_b上不存在完全匹配,但是对于该特定id_a只有一个条目all_info,我们假设这是我们想要的(并替换some_data中损坏的id_b)
所以,给定两个表,
some_data all_info
id_a | id_b id_a | id_b | val
------------ --------------------
1 | a 1 | a | v_i
2 | b 2 | c | v_x
3 | c 2 | b | v_ii
4 | d 3 | d | v_iv
3 | e | v_v
4 | f | v_vi
我想获得:
id_a | id_b | val
------------------
1 | a | v_i
2 | b | v_ii
3 | c | NULL
4 | f | v_vi
到目前为止,我已经想到了两种方法,其中一种方法是基本的:
SELECT sd.*, ai.val
FROM some_data sd
LEFT OUTER JOIN all_info ai
ON sd.id_a = ai.id_a
AND (sd.id_b = ai.id_b OR COUNT(*) = 1)
当然这本身不起作用(也没有完成我替换坏id_b的第二个目标),但尝试用COUNT()函数进行各种分组和选择我找不到SQL发现的任何东西足以运行。我还想尝试使用SET命令填充列,但又找不到使其工作的方法。
作为旁注,看看数据似乎all_info在AT MOST上有一行与id_a和id_b上的some_data匹配。此外,当id_a和id_b匹配时,考虑到id_b的复杂性,可以安全地假设匹配是正确的。
答案 0 :(得分:1)
您的选择将是这样的:
SELECT sd.id_a, sd.id_b,
CASE WHEN ai.id_a IS NULL THEN ai2.val ELSE ai.val END as val
FROM some_data sd
LEFT JOIN all_info ai
ON ad.id_a = ai.id_a AND ad_id_b = ai.id_b
LEFT JOIN
(SELECT id_a, MIN(id_b) id_b, MIN(val) val
FROM all_info
GROUP BY id_a
HAVING COUNT(*) = 1
) ai2 ON sd.id_a = ai.id_a
答案 1 :(得分:0)
您可以运行此操作来修复您的数据:
UPDATE some_data sd
JOIN
(SELECT id_a, MIN(id_b) id_b
FROM all_info
GROUP BY id_a
HAVING COUNT(*) = 1
) ai ON sd.id_a = ai.id_a AND sd.id_b <> ai.id_b
SET ad.id_b = ai.id_b