我操作MySQL的惊险一幕( 二 )


我:如何解决的?
组长:将这个事务回滚解决的,你更新的 SQL 怎么写的?(努力回想)
于是写出了上面写的 SQL:
UPDATE b AS tb, (SELECT create_time FROM a) AS ta SET tb.create_time = ta.create_time;组长:你为什么这样写?不应该把子查询写在 SET tb.create_time 后面吗?
我:对啊,我一开始就是把这个子查询写在它后面的,但是提示我语法错误,我就换了一种写法 。
组长:那你写写你说提示错误的 SQL 。
于是我又丢出来一个 SQL:
UPDATE b SET create_time = (SELECT create_time FROM a);实际上,这条 SQL 也是不行的 , 子查询返回的结果不止一行,而当前 SET 是更新某一行的 。
正确的写法是:
UPDATE b AS tbSET create_time = (SELECT create_time FROM a AS ta WHERE tb.id = ta.id AND tb.name = ta.name)WHERE tb.id = (SELECT tb.id FROM a AS ta WHERE tb.id = ta.id AND tb.name = ta.name)

我操作MySQL的惊险一幕

文章插图
博客园-SQL把一个表中数据更新到另一个表的多种方法
最后组长深思 , 你 B 表已经有 2 万多条记录了,A 表也有 2 万多条记录 , 你这样更新,每一次都需要子查询查出 A 表的 2 万多条记录,B 也有 2 万多条记录 , 这样成笛卡尔积了,你知道什么是笛卡尔积吧?2 万 × 2 万 = 4 亿的记录行了,难怪这么久 。
总结情况:漏了某一个字段 X,需要将 A 表的这个字段列值更新到 B 表
条件:A 中的 id 字段的值等于 B表中的 id 字段的值 且 A 中的 name 字段的值等于 B 中 name 字段的值(条件为什么这样写?) 。
条件这样写主要是因为 表和表之间的关联关系 可能有多个字段,此处只选二个字段,多个依此类推 。
操作:
  • 一张表的数据插入到另一张表,可以这样写:
INSERT INTO 目标表(字段1, 字段2, ...) SELECT 字段1, 字段2, ... FROM 来源表 WHERE 条件;
  • 批量更新一张表的某个字段到另一张表,那么 SQL 可以类似这样写:
UPDATE b AS tbSET create_time = (SELECT create_time FROM a AS ta WHERE tb.id = ta.id AND tb.name = ta.name)WHERE tb.id = (SELECT tb.id FROM a AS ta WHERE tb.id = ta.id AND tb.name = ta.name)所谓洗数据:在我的理解中,就是把旧数据 , 按照新数据的规则把旧数据不正确的值修改正确,同时把这些旧数据插入到新数据中,成为新数据 。举个例子 , A 表中的 province_id,值为 10 代表 广东,而 B 表中的 province_id  , 值为 19 代表 广东,把 A 表中的数据插入到 B 表的过程中,把值为 10 修改为 19 , 这样插入的数据才能在 B 表中正确表示 广东,这个过程就是「洗数据」,当然 , 也可以在插入后再修改,不管过程是怎样,最终能把数据的值修改正确 , 就是洗数据!
教训:
  1. 数据量大的表,少在测试环境操作,要操作尽量保证写的 SQL 是正确的,能在本地环境操作就现在本地环境操作!
  2. 能用 Java 代码进行操作,优先写 Java 代码操作!
最后的最后由本人水平所限,难免有错误以及不足之处,屏幕前的靓仔靓女们 如有发现,恳请指出!
最后 , 谢谢你看到这里,谢谢你认真对待我的努力,希望这篇博客对你有所帮助!
你轻轻地点了个赞,那将在我的心里世界增添一颗明亮而耀眼的星!

推荐阅读