如何实现update select 语句

简介: ​ 这次的文章出现也是因为这样一个类似的需求,个人需要把一个30万行(后续会发文介绍常见的处理手段)的数据文件入库,同时需要将部分字段迁移到另一张表,两个表之间通过两个字段进行and匹配。

前言:


有些时候我们会遇到如下情况,我们需要依赖一张表的查询结果来更新另一张表,比如我们存在一张主表和一张关联表,我们需要把关联表的部分字段数据同步到主表的里面。


这次的文章出现也是因为这样一个类似的需求,个人需要把一个30万行(后续会发文介绍常见的处理手段)的数据文件入库,同时需要将部分字段迁移到另一张表,两个表之间通过两个字段进行and匹配。下面画一下结构图:

image.png


处理方式也比较简单,直接使用sql就可以完成,这篇文章针对这个小需求,总结一下update select 的几种实现方式。


文章目的:


1.实现update select 的几种常见方法


1.join

2.merge

3.子查询


2.merge的踩坑和问题


准备数据


为了更好的进行实际操作,这里构建两张简单的表来模拟场景。直接复制下面的db即可,由于不同数据库sql不同,这里使用的是postgreSql 数据库。


旧表


CREATE TABLE "public"."olddb" (
  "id" int4 NOT NULL,
  "relevance1" varchar(255) COLLATE "pg_catalog"."default",
  "relevance2" varchar(255) COLLATE "pg_catalog"."default",
  "new_field" varchar(255) COLLATE "pg_catalog"."default",
  CONSTRAINT "olddb_pkey" PRIMARY KEY ("id")
)
;
ALTER TABLE "public"."olddb" 
  OWNER TO "postgres";
COMMENT ON COLUMN "public"."olddb"."id" IS '主键';
COMMENT ON COLUMN "public"."olddb"."relevance1" IS '关联字段1';
COMMENT ON COLUMN "public"."olddb"."relevance2" IS '关联字段2';
COMMENT ON COLUMN "public"."olddb"."new_field" IS '新字段,需要由关联表同步';


表成功创建之后,在内部加入一些简单的数据:


image.png


新表


CREATE TABLE "public"."newdb" (
  "id" int4 NOT NULL,
  "relevance1" varchar(255) COLLATE "pg_catalog"."default",
  "relevance2" varchar(255) COLLATE "pg_catalog"."default",
  "new_field" varchar(255) COLLATE "pg_catalog"."default",
  CONSTRAINT "newdb_pkey" PRIMARY KEY ("id")
)
;
ALTER TABLE "public"."newdb" 
  OWNER TO "postgres";
COMMENT ON COLUMN "public"."newdb"."id" IS '主键';
COMMENT ON COLUMN "public"."newdb"."relevance1" IS '关联字段1';
COMMENT ON COLUMN "public"."newdb"."relevance2" IS '关联字段2';
COMMENT ON COLUMN "public"."newdb"."new_field" IS '新字段,需要同步到旧表';


提醒:注意数据库是postgresql,其他数据库可能存在字段等差别而无法成功


表成功创建之后,在内部加入一些简单的数据:


image.png


实现方式汇总


join


第一种的连接方式使用的是连接表的join方法,我们通过关联字段查出对应的关联记录,同时在关联之后将关联新字段的数据更新到旧表,这样就实现了每关联一条记录就更新一条记录数据:


实现方式也比较简单,只需要使用


UPDATE olddb aa
SET new_field = bb.new_field
FROM
   newdb bb where aa.relevance1 = bb.relevance1 
  AND aa.relevance2 = bb.relevance2


他的执行结果如下:


image.png


下面的下方是错的,这时候sql会抛出一个错误。


UPDATE olddb ALIAS 
SET ( new_field ) = (
  SELECT
    ( bb.new_field ) 
  FROM
    olddb aa
    JOIN newdb bb ON aa.relevance2 = bb.relevance2 
    AND aa.relevance1 = bb.relevance1 
  )


Merge(未验证)


第二种方式可能比较陌生,因为merge算是对于insert以及update的一个统合,粗略了解了一下发现能干不少事情,下面说下。

注意下面的方法在postgresql 报错,原因是是我的postgresql版本太低,但是个人在升级过后还不能支持使用merge方法 ,所以这里保存了sql,可以改动后尝试到其它的数据库语言进行使用。


ERROR:  syntax error at or near "MERGE"

很头疼,在stackflow也没用找到答案。


merge into olddb as olds
using newdb news on olds.new_field = news.new_field
when matched
update set 
olds.new_field = news.new_field

需要注意的是不同的数据库对于merge的特性是不一致的,建议查看当前安装数据库的版本以及文档进行确认比较稳妥。


下面是 postgresqlmerge使用案例,注意一般建议版本为11以上再使用merge


MERGE INTO wines 
USING (VALUES('Chateau Lafite 2003', '24')) v
ON v.column1 = w.winename
WHEN NOT MATCHED 
  INSERT VALUES(v.column1, v.column2)
WHEN MATCHED
  UPDATE SET stock = stock + v.column2;

子查询


子查询是最简单也是最容易想到的一种方式,不过子查询有一个明显的缺点就是数据量较大的情况下通常性能都比较差, 这种操作通常适合数据量比较小的情况,下面是对应的案例语法:


UPDATE olddb 
SET new_field = ( SELECT newdb.new_field FROM newdb WHERE olddb.relevance1 = newdb.relevance1 AND olddb.relevance2 = newdb.relevance2 )

下面是子查询需要注意的点:


  • 如果子查询无法找到任何匹配的行,则更新后的值将被更改为NULL
  • 如果子查询找到多个匹配的行,update查询将返回一个错误。


错误的信息如下:

> ERROR:  more than one row returned by a subquery used as an expression

(>错误:作为表达式使用的子查询返回多行)


  • 多数情况下子查询的性能较差,尽量避免使用


总结:


由于merge个人使用经验不足,花了较多时间依然没有解决,所以文章标题进行了标记,后续使用了其他的方式避开问题。


update select的实现实际情况复杂多变,这里只列举了最简单的使用情况。

相关实践学习
使用PolarDB和ECS搭建门户网站
本场景主要介绍如何基于PolarDB和ECS实现搭建门户网站。
阿里云数据库产品家族及特性
阿里云智能数据库产品团队一直致力于不断健全产品体系,提升产品性能,打磨产品功能,从而帮助客户实现更加极致的弹性能力、具备更强的扩展能力、并利用云设施进一步降低企业成本。以云原生+分布式为核心技术抓手,打造以自研的在线事务型(OLTP)数据库Polar DB和在线分析型(OLAP)数据库Analytic DB为代表的新一代企业级云原生数据库产品体系, 结合NoSQL数据库、数据库生态工具、云原生智能化数据库管控平台,为阿里巴巴经济体以及各个行业的企业客户和开发者提供从公共云到混合云再到私有云的完整解决方案,提供基于云基础设施进行数据从处理、到存储、再到计算与分析的一体化解决方案。本节课带你了解阿里云数据库产品家族及特性。
相关文章
|
7天前
|
人工智能 数据可视化 安全
王炸组合!阿里云 OpenClaw X 飞书 CLI,开启 Agent 基建狂潮!(附带免费使用6个月服务器)
本文详解如何用阿里云Lighthouse一键部署OpenClaw,结合飞书CLI等工具,让AI真正“动手”——自动群发、生成科研日报、整理知识库。核心理念:未来软件应为AI而生,CLI即AI的“手脚”,实现高效、安全、可控的智能自动化。
34458 17
王炸组合!阿里云 OpenClaw X 飞书 CLI,开启 Agent 基建狂潮!(附带免费使用6个月服务器)
|
18天前
|
人工智能 JSON 机器人
让龙虾成为你的“公众号分身” | 阿里云服务器玩Openclaw
本文带你零成本玩转OpenClaw:学生认证白嫖6个月阿里云服务器,手把手配置飞书机器人、接入免费/高性价比AI模型(NVIDIA/通义),并打造微信公众号“全自动分身”——实时抓热榜、AI选题拆解、一键发布草稿,5分钟完成热点→文章全流程!
45286 142
让龙虾成为你的“公众号分身” | 阿里云服务器玩Openclaw
|
8天前
|
人工智能 JSON 监控
Claude Code 源码泄露:一份价值亿元的 AI 工程公开课
我以为顶级 AI 产品的护城河是模型。读完这 51.2 万行泄露的源码,我发现自己错了。
4835 20
|
1天前
|
人工智能 自然语言处理 安全
Claude Code 全攻略:命令大全 + 实战工作流(建议收藏)
本文介绍了Claude Code终端AI助手的使用指南,主要内容包括:1)常用命令如版本查看、项目启动和更新;2)三种工作模式切换及界面说明;3)核心功能指令速查表,包含初始化、压缩对话、清除历史等操作;4)详细解析了/init、/help、/clear、/compact、/memory等关键命令的使用场景和语法。文章通过丰富的界面截图和场景示例,帮助开发者快速掌握如何通过命令行和交互界面高效使用Claude Code进行项目开发,特别强调了CLAUDE.md文件作为项目知识库的核心作用。
1704 5
Claude Code 全攻略:命令大全 + 实战工作流(建议收藏)
|
7天前
|
人工智能 API 开发者
阿里云百炼 Coding Plan 售罄、Lite 停售、Pro 抢不到?最新解决方案
阿里云百炼Coding Plan Lite已停售,Pro版每日9:30限量抢购难度大。本文解析原因,并提供两大方案:①掌握技巧抢购Pro版;②直接使用百炼平台按量付费——新用户赠100万Tokens,支持Qwen3.5-Max等满血模型,灵活低成本。
1737 5
阿里云百炼 Coding Plan 售罄、Lite 停售、Pro 抢不到?最新解决方案