SQL Server跨表更新:用Table1字段更新Table2同CN值的单行数据
解决方案:用Table1更新Table2中每个CN对应的单条记录
嘿,这个需求很清晰——就是要给Table2里每个CN分组只更新一行的SLT值,用Table1里对应的数值,其余行保持原0值不变。下面我针对几种主流数据库给出具体实现,你按需选用就行!
MySQL 实现方式
MySQL可以通过给Table2的记录按CN分组生成行号,精准定位要更新的那一行:
-- 先给Table2标记分组内的行号,再关联Table1更新目标行 UPDATE Table2 t2 JOIN ( SELECT CN, -- 如果Table2有唯一主键(比如ID),这里用主键替代SLT关联更准确 SLT, ROW_NUMBER() OVER (PARTITION BY CN ORDER BY (SELECT NULL)) AS rn FROM Table2 ) t2_rn ON t2.CN = t2_rn.CN AND t2.SLT = t2_rn.SLT JOIN Table1 t1 ON t2_rn.CN = t1.CN SET t2.SLT = t1.SLT WHERE t2_rn.rn = 1;
小提示:如果Table2有唯一主键,关联时用主键替换SLT能避免重复值导致的错误,更稳妥。
SQL Server 实现方式
用CTE(公用表表达式)结合窗口函数标记目标行,操作起来更直观:
WITH RankedTable2 AS ( SELECT CN, SLT, -- 这里ORDER BY可以换成具体字段,比如按创建时间排序,固定更新某一行 ROW_NUMBER() OVER (PARTITION BY CN ORDER BY (SELECT NULL)) AS rn FROM Table2 ) UPDATE RankedTable2 SET SLT = t1.SLT FROM RankedTable2 rt2 JOIN Table1 t1 ON rt2.CN = t1.CN WHERE rt2.rn = 1;
ORDER BY (SELECT NULL) 表示随机选一行更新,如果需要固定更新某一行(比如最早录入的),替换成对应的排序字段就行,比如ORDER BY CreateTime ASC。
Oracle 实现方式
Oracle可以利用ROWID来定位要更新的行,逻辑同样清晰:
UPDATE Table2 t2 SET SLT = (SELECT t1.SLT FROM Table1 t1 WHERE t1.CN = t2.CN) WHERE ROWID IN ( SELECT ROWID FROM ( SELECT ROWID, ROW_NUMBER() OVER (PARTITION BY CN ORDER BY (SELECT NULL)) AS rn FROM Table2 ) WHERE rn = 1 );
同样,这里的排序规则可以根据你的实际需求调整,确保更新你期望的那一行。
执行后验证结果
不管用哪种方式,执行完成后Table2的数据都会变成你想要的样子:
CN | SLT
1 | 1.2
1 | 0
1 | 0
2 | 19
2 | 0
3 | 23
内容的提问来源于stack exchange,提问作者Amir Abhari
相关产品推荐
相关产品推荐

