Oracle高效数据同步实战:MERGE INTO语句的进阶应用

Oracle merge into 详解(有则更新,无则插入) 阅读详情

1. 从“笨办法”到“聪明活儿”:为什么你需要MERGE INTO

如果你在维护一个系统,比如一个电商后台或者一个客户关系管理平台,你肯定遇到过这种头疼事:每天都有新的数据从各个渠道涌进来,比如新注册的用户、新下的订单、更新的产品价格。你的任务是把这些新数据,准确地“合并”到主数据库里。遇到主键已经存在的记录,就更新它;遇到全新的记录,就插入它。

在没学会 MERGE INTO 之前,我们是怎么干的?我猜很多人和我一样,写过下面这种“经典”的脚本:

-- 先尝试更新
UPDATE target_table t
SET t.name = s.name,
    t.email = s.email
FROM source_table s
WHERE t.id = s.id;

-- 然后处理没被更新到的,也就是需要插入的新数据
INSERT INTO target_table (id, name, email)
SELECT s.id, s.name, s.email
FROM source_table s
WHERE NOT EXISTS (SELECT 1 FROM target_table t WHERE t.id = s.id);

看起来逻辑挺清晰,对吧?但这里有两个大坑。第一,性能问题。你需要对源表和目标表进行两次全表扫描和关联,数据量一大,速度就慢下来了。第二,更致命的是数据一致性问题。想象一下,在你执行完 UPDATE 之后、执行 INSERT 之前的那个瞬间,如果有另一个程序恰好往 target_table 里插入了同一条记录,你的 INSERT 语句就会因为主键冲突而失败。为了解决这个,你可能还得加事务锁,把整个操作包起来,代码变得更复杂,对数据库的压力也更大了。

MERGE INTO 就是为了终结这种“先更新再插入”的笨拙操作而生的。它把“查找、比较、更新或插入”这一整套逻辑,封装成了一条原子性的 SQL 语句。数据库引擎会一次性处理好所有匹配和不匹配的记录,既保证了操作的原子性和数据一致性,又因为只需要一次全表扫描和关联,在大数据量下的性能优势非常明显。我把它叫做“一条语句搞定增删改查里的‘改’和‘增’”,是 Oracle 里处理数据同步和合并的“瑞士军刀”。

2. 庖丁解牛:拆解MERGE INTO的每一个部件

别看 MERGE INTO 功能强大,它的语法结构其实非常规整,像搭积木一样。咱们来彻底拆解一遍,理解了每个部件,你就能随心所欲地组合它们了。

最基本的架子长这样:

MERGE INTO 目标表 [目标表别名]
USING 源表或子查询 [源表别名]
ON (匹配条件)
WHEN MATCHED THEN
    UPDATE SET 列1 = 值1, 列2 = 值2 ...
    [WHERE 更新条件]
WHEN NOT MATCHED THEN
    INSERT (列1, 列2, ...) VALUES (值1, 值2, ...)
    [WHERE 插入条件];

我来给你翻译一下:

  • MERGE INTO 目标表:你想把数据合并到哪张表里?就是它了。
  • USING ... ON (...):这是“找朋友”的环节。USING 后面可以是一张物理表,也可以是一个复杂的子查询结果集。ON 后面就是“认亲”的条件,比如 ON (目标表.员工ID = 源表.员工ID)。这个条件决定了哪些记录是“老朋友”(已存在),哪些是“新朋友”(不存在)。
  • WHEN MATCHED THEN UPDATE:找到老朋友了怎么办?通常是更新它的信息。SET 后面就是你要给老朋友的新数据。
  • WHEN NOT MATCHED THEN INSERT:遇到新朋友了,那就欢迎他加入,执行插入操作。

这里有两个高级玩法,很多教程里一笔带过,但在实战中特别有用:

  1. 可选的 WHERE 子句:在 UPDATE 或 INSERT 后面,你还可以加一个 WHERE。这是什么意思?它是对“是否要执行这个更新或插入”做二次判断。比如,即使 ON 条件匹配上了(是“老朋友”),但如果他的新工资不比老工资高,我们可能就不想更新。这个 WHERE 子句给了我们这种精细控制的能力。
  2. DELETE 子句(Oracle 10g及以上):这是一个隐藏的“大招”。你可以在 WHEN MATCHED THEN UPDATE 后面,再接一个 DELETE WHERE ...。它的作用是:在更新完一条匹配的记录后,立刻检查一个删除条件,如果满足,就把这条刚更新完的记录删除掉!这在做数据归档或清理过期数据时非常高效。语法是:WHEN MATCHED THEN UPDATE ... DELETE WHERE 删除条件。注意,删除条件只能引用目标表的列或者 UPDATE SET 中设置的新值。

为了让你看得更清楚,我把核心部件和它们的作用总结成了下面这个表:

语法部件是否必须作用与说明实战技巧
MERGE INTO 目标表是指定数据合并的目的地。建议始终使用表别名,后续SQL会更简洁。
USING 源是指定数据来源。可以是表、视图,或一个子查询。子查询是灵魂,可以在这里做过滤、聚合、多表关联,准备好最干净的源数据。
ON (条件)是定义源和目标记录如何匹配(如用主键、业务键)。这是性能关键点,条件应基于索引列,否则会引发全表扫描。
WHEN MATCHED THEN UPDATE否对匹配的记录执行更新操作。可以配合 WHERE 子句实现有条件更新,避免不必要的写操作。
WHEN NOT MATCHED THEN INSERT否对不匹配的记录执行插入操作。可以配合 WHERE 子句实现有条件插入,过滤掉不需要的数据。
DELETE WHERE否在 UPDATE 后,可选的删除操作(Oracle特有)。用于在合并同时清理数据(如标记删除、归档)。条件只能基于目标表列或UPDATE后的新值。

3. 实战进阶:从简单同步到复杂业务逻辑

光说不练假把式,咱们直接看几个我在项目中真实用到的,比基础教程复杂得多的案例。你会发现,MERGE INTO 的威力,大半藏在 USING 后面的那个子查询里。

3.1 场景一:带版本控制的增量同步

这是数据仓库和ETL里最常见的场景。源系统每天给你一个全量数据文件,但你不能傻傻地全部覆盖。你需要判断哪些是真正新增或修改过的。

假设我们有一个 products_source 表,每天凌晨同步过来。我们有自己的 products 表,里面有 last_updated 字段记录我们最后一次更新的时间。

MERGE INTO products p
USING (
    SELECT product_id, product_name, price, category, update_time
    FROM products_source
    WHERE update_time > (SELECT MAX(last_updated) FROM products)
    -- 只同步自上次同步以来有变化的数据
) src
ON (p.product_id = src.product_id)
WHEN MATCHED THEN
    UPDATE SET
        p.product_name = src.product_name,
        p.price = src.price,
        p.category = src.category,
        p.last_updated = src.update_time
    WHERE
        p.product_name <> src.product_name
        OR p.price <> src.price
        OR p.category <> src.category
        -- 避免相同数据的无意义更新
WHEN NOT MATCHED THEN
    INSERT (product_id, product_name, price, category, last_updated)
    VALUES (src.product_id, src.product_name, src.price, src.category, src.update_time);

提示:USING 子查询里的 WHERE update_time > ... 是增量同步的关键。它极大地减少了需要处理的数据量。而 UPDATE 后面的 WHERE 子句,则避免了字段值完全没变动的记录发生不必要的更新,减少redo日志生成,对性能和环境都友好。

3.2 场景二:多源关联与复杂条件更新

现在需求升级了。你的数据来源不止一个表,你需要把它们关联起来,并且更新逻辑也更复杂。比如,你要根据员工的绩效评分(来自 performance 表)和所在部门的预算情况(来自 departments 表),来决定是否给员工加薪,以及加多少。

MERGE INTO employees e
USING (
    SELECT
        e.emp_id,
        e.salary as old_salary,
        p.rating,
        d.budget_status,
        -- 复杂的业务逻辑计算放在子查询里
        CASE
            WHEN p.rating = 'A' AND d.budget_status = 'HEALTHY' THEN e.salary * 1.15
            WHEN p.rating = 'B' AND d.budget_status = 'HEALTHY' THEN e.salary * 1.10
            WHEN p.rating = 'A' AND d.budget_status = 'TIGHT' THEN e.salary * 1.05
            ELSE e.salary -- 其他情况不调薪
        END AS proposed_salary
    FROM employees e
    JOIN performance p ON e.emp_id = p.emp_id AND p.year = 2023
    JOIN departments d ON e.dept_id = d.dept_id
) src
ON (e.emp_id = src.emp_id)
WHEN MATCHED THEN
    UPDATE SET
        e.salary = src.proposed_salary,
        e.last_salary_adjust = SYSDATE
    WHERE
        src.proposed_salary <> e.salary -- 只有薪资有变化才更新
        AND src.proposed_salary IS NOT NULL;

这个例子展示了 MERGE INTO 处理复杂业务逻辑的能力。所有数据准备和计算都在 USING 子查询中完成,主语句非常清晰:匹配上,且薪资有变化,就更新。这比写多个独立的 UPDATE 语句清晰、高效得多。

3.3 场景三:使用DELETE子句进行同步清理

前面提到过 DELETE 子句,这里来个具体例子。假设我们有一个用户配置表 user_settings,源表 settings_updates 会推送新的配置。如果某个配置项的值被更新为 ‘DELETE’ 这个特殊标记,我们希望在同步后,直接删除目标表中的这条配置记录。

MERGE INTO user_settings tgt
USING settings_updates src
ON (tgt.user_id = src.user_id AND tgt.setting_key = src.setting_key)
WHEN MATCHED THEN
    UPDATE SET
        tgt.setting_value = src.setting_value,
        tgt.updated_at = SYSDATE
    DELETE WHERE
        tgt.setting_value = 'DELETE' -- 注意:这里判断的是UPDATE之后的新值!
WHEN NOT MATCHED THEN
    INSERT (user_id, setting_key, setting_value, updated_at)
    VALUES (src.user_id, src.setting_key, src.setting_value, SYSDATE)
    WHERE
        src.setting_value <> 'DELETE'; -- 源数据就是DELETE的,直接不插入

这个操作非常高效且原子性。它在一个语句里完成了:更新现有配置、删除需要清理的配置、插入新配置。DELETE WHERE 是 UPDATE 动作的一部分,它检查的是执行 UPDATE SET 之后的目标表记录状态。

4. 性能调优与避坑指南

功能强大,但用不好也会踩坑。下面是我总结的几个关键性能点和常见陷阱。

1. 索引是生命线 ON 子句里的匹配条件,一定要走索引。通常这就是主键或唯一约束。如果 ON (t.id = s.id),那么 t.id 上必须有索引。如果没有,每次合并都是一次全表扫描灾难。你可以通过执行计划 (EXPLAIN PLAN) 来确认是否使用了索引。

2. 善用子查询过滤 尽可能在 USING 的子查询里,把不需要的数据过滤掉。不要直接把一个几千万行的物理表丢到 USING 里。就像前面的增量同步例子,先通过时间戳过滤出最小数据集。如果源数据需要关联,也尽量在子查询里完成,让中间结果集尽可能小。

3. 小心空值(NULL)陷阱 这是最容易出错的地方。在 ON 条件或者 UPDATE 的 WHERE 条件里,如果有字段可能为 NULL,要特别注意。在 Oracle 里,NULL = NULL 的结果不是 TRUE,而是 UNKNOWN(相当于 FALSE)。这会导致你预期中应该匹配上的记录,因为 NULL 比较而匹配失败。

-- 错误示例:如果 email 字段存在 NULL,匹配会出问题
ON (t.email = s.email)

-- 正确做法:使用 NVL 函数或更安全的比较方式
ON (NVL(t.email, 'N/A') = NVL(s.email, 'N/A'))
-- 或者,如果业务允许,在同步前先清理掉NULL值

4. 控制事务大小 MERGE INTO 是一个原子操作,它要么全部成功,要么全部失败。如果你一次性同步几百万行数据,这个事务会非常庞大,可能产生大量的undo和redo日志,甚至导致锁表。对于超大批量同步,我建议采用分批策略,比如按时间范围或ID范围进行循环提交。

5. 权限问题 执行 MERGE INTO 的用户,必须对目标表有 INSERT、UPDATE 权限,如果使用了 DELETE 子句,还需要 DELETE 权限。对 USING 后面的源表或视图,需要有 SELECT 权限。

5. 超越MERGE:与其他方案的对比

MERGE INTO 不是万能的,了解它的替代方案,能让你在正确的地方使用正确的工具。

对比 INSERT ALL + UPDATE: 对于简单的“有则更新,无则插入”,有些老司机会用 INSERT ALL 配合 WHERE NOT EXISTS 再外加一个 UPDATE。这在某些简单场景下可能写法更直观,但 MERGE INTO 在语义清晰性、原子性和性能(单次扫描)上通常更优。

对比存储过程循环: 新手最容易犯的错误就是写个游标(CURSOR),在循环里一条条地 SELECT ... FOR UPDATE,然后判断 INSERT 或 UPDATE。这是性能最差的方法,因为每次循环都是一次网络交互和SQL解析。MERGE INTO 是面向集合的操作,比过程式的循环快几个数量级。

对比物化视图(Materialized View)刷新: 如果你的需求只是定期将远程数据或复杂查询结果快照到本地,那么物化视图可能是更好的选择。它可以设置定时自动刷新,并且支持增量刷新(FAST REFRESH)。MERGE INTO 更适用于需要定制复杂业务逻辑的、主动触发的数据同步场景。

说到底,MERGE INTO 是你 SQL 工具箱里的一件利器。它最适合那些基于键值匹配、需要原子性“更新或插入”的场景。当你下次再写“先查再判再插或改”的脚本时,停下来想想,是不是该请出 MERGE INTO 这位老朋友了。把它用熟了,你会发现很多繁琐的数据整合工作,都能变得优雅而高效。

Oracle MERGE INTO实战:用一条SQL搞定员工数据同步(附完整案例) 本文详细介绍了Oracle MERGE INTO语句在员工数据同步中的高效应用,通过实战案例展示如何用一条SQL实现数据的插入、更新和条件处理。文章深入解析MERGE INTO的高级语法,提供性能优化技巧和常见问题解决方案,是提升数据库操作效率的终极指南。 阅读详情

相关推荐

SAP-PP MD04详解一

MD04是SAP运行MRP后的结果查询事务码,其他功能强大,标准功能比如:查询/更改物料主数据、转换计划订单到生产订单/采购申请、查询/更改各个MRP元素对应的单据等等。而且还可以附加标准的菜单或者自定义添加事务码上去。老铁将做一个MD04详细说明系列,本篇为第一篇之MRP元素说明。 我们来看看MD04基本界面 可以看到主要的数据显示界面,有日期、MRP元素、MRP元素数据、再计划日期、收货/需求、可用数量、工厂、库存地点等栏位。光标定位到MRP元素列,按F1即可看到各类MRP元素的说...

weixin_52158549的博客 1万+

Oracle中merge into的使用方法

一、用途: 可以同时从1个或者多个源表对目标表进行更新、插入、删除数据,经常用于操作大量的数据,即对于大批量的数据更新、插入时效率极高。 二、语法: merge into table_name alias1 --目标表 可以用别名 using (table|view|sub_query) alias2 --数据源表 可以是表、视图、子查询 on (join condition) --关联条件 when matched then --当关联...

蓝星部队的博客 3万+

新买的USB无线网卡插上没反应?保姆级排查指南:从设备管理器到网络列表

本文提供USB无线网卡无法识别的全流程排查手册,涵盖硬件检测、驱动管理和网络配置三大维度。重点解析设备管理器中的设备状态诊断和驱动解决方案,特别适用于Realtek芯片的无线网卡(如RTL8188GU、RTL8812BU等),帮助用户快速解决网卡插上无反应的问题。

weixin_29876033的博客 503

Oracle MERGE INTO实战:如何用一条SQL搞定员工数据同步(含多表关联案例)

本文深入解析Oracle数据库的MERGE INTO高级语法,通过员工数据同步的实战案例,详细演示如何用一条SQL语句高效完成数据的更新与插入操作。文章涵盖从基础语法到多表关联同步的复杂场景,并提供了性能优化与错误处理等高级技巧,帮助开发者简化数据同步流程,提升数据库操作效率。

oil88的博客 778

科研绘图(二):R 语言实现小鼠脑图谱 3D 渲染,附完整代码与数据获取指南

在生物医学科研中,脑区的 3D 可视化是呈现实验结果、解析脑结构功能的重要手段。R 语言凭借rgl和Rvcg等工具包,可高效实现小鼠全脑及特定脑区(如 CA1 区)的立体渲染,且代码可复用性强。本文将从环境搭建、数据准备、代码实现到结果导出,手把手带你完成小鼠脑图谱 3D 绘图,小白也能快速上手!

good_rrrrr的博客 2023

避坑指南:WSL2网络模式修改导致无法上网的解决方案(附备份还原技巧)

本文深入解析WSL2默认网络隔离机制,并提供三种安全的端口互通方案,重点推荐通过配置Windows防火墙规则实现稳定访问。同时,针对网络配置修改可能引发的无法上网问题,给出了从重置配置到系统级备份的完整恢复指南,确保开发环境安全可靠。

jj890的博客 781

ORACLE进阶(十一)MERGE INTO学习总结

在工作中,查看到类似于如下的SQL语句: 语句是新增的语法,用来合并和语句。通过语句,根据一张表或子查询的连接条件对另外一张表进行查询,连接条件匹配上的进行,无法匹配的执行。这个语法仅需要一次全表扫描就完成了全部工作,执行效率要高于。例如,有一个表T,有两个字段a、b,我们想在表T中做,如果条件满足,则更新T中b的值,否则在T中插入一条记录。在Microsoft的SQL语法中,很简单的一句判断就可以了,中的语法如下: Oracle中,要实现相同的功能,要用到来实现(Oracle 9i引入的功能),其语法如下

IT全栈 华强工作室 2780

使用STM32制作简易数字时钟

连接LED数码管的电源和地线到STM32单片机的对应引脚,将数码管的A、B、C、D引脚连接到STM32单片机的I/O口引脚。通过编写和调试这个项目,可以熟悉STM32单片机的GPIO口和定时器的使用,以及数字显示的控制。步骤六:测试和调试 通过观察数码管的显示,可以验证时钟功能是否正常工作。步骤四:编写代码 在主程序中,我们将使用定时器中断来控制时钟的运行,并使用GPIO口控制LED数码管的显示。步骤五:编译和下载 编译代码并下载到STM32单片机中,通过调试器和串口监视器进行调试和查看输出结果。

qq_67153941的博客 1303

Oracle MERGE INTO语法详解

在Oracle数据库中,我们经常需要根据某些条件来决定是插入新数据还是更新现有数据。传统的做法是先查询数据是否存在,然后分别执行INSERT或UPDATE操作,这样不仅代码复杂,而且性能不佳。Oracle的MERGE INTO语句完美解决了这个问题,它可以在一条语句中同时处理插入和更新操作,让我们的数据操作更加高效和简洁。

七一 1579

STM32实战开发(65):STM32摄像头图像采集开发教程

我们将会详细介绍如何使用STM32进行摄像头控制、图像数据采集以及如何将采集到的图像数据传输到其他设备进行处理。通过这篇博客,您将能够掌握STM32与摄像头模块的图像采集技术,应用于各种图像处理场景。为了确保STM32能够正确接收图像数据,我们需要配置STM32的GPIO引脚,并通过外部中断捕获这些信号。为了实现更高效的图像采集,可以通过DMA进行数据传输,将图像数据直接从GPIO引脚存储到内存中。通过DMA传输,我们可以将采集到的图像数据直接存储在内存中的一个缓冲区,然后进行后续的图像处理。

2201_76125393的博客 2538

北斗导航 | ILS(仪表着陆系统)、MLS(微波着陆系统)和GBAS(地基增强系统)的性能对比

最 早 的 GBAS 系 统 是 **局 域 增 强 系 统(LAAS)**,它是 1990 年由美国 Honeywell 公司 和 NASA 共 同 完 成 的 差 分 GPS(DGPS)演 变 而 来 的。1998 年,LAAS 被 ICAO 采 纳为 GBAS。2009 年 9 月 3 日 Honeywell 公 司 的GBAS 系统通过了 **CAT-I 精密进近着陆系统**的设计认证 ,而 **CAT-II 和 CAT-III 系统的研发和验证工作也正在有序的进行中**

尘世冰封的专栏 3986

1小时搭建数据同步原型:Oracle MERGE INTO实战

源表:存储从旧系统导出的客户数据目标表:新系统的客户主表同步规则:新客户直接插入已存在客户更新联系方式以客户ID作为匹配键。

CrystalwaveStag的博客 654

(五)深入理解蓝牙BLE之“Beacon包格式详解”

蓝牙Beacon格式详解 本文重点在结合Bluetooth官网spec和几个例子来使beacon帧格式更加容易被理解。 广播帧格式: 首先beacon是蓝牙BLE广播包的一种,蓝牙广播帧格式如下: PS:其实BLE数据帧除了报头字段和数据字段定义与广播帧不同之外,前导/接入地址/长度/校验格式均相同。 广播帧数据字段格式: 数据字段最长为37个字节:6个字节的广播设备地址 + 31个字节广播数据。 广播数据的格式如下:AD Structure1 +AD Structure2 + .....

1万+

用快马 AI 一键生成 Oracle MERGE INTO 数据同步应用,效率提升 200%!

这种"AI生成+人工优化"的模式,特别适合快速迭代的业务场景。最近在做一个数据迁移项目,需要频繁同步两个Oracle数据库表的数据。更省心的是部署环节。传统方式要折腾服务器配置,在快马直接点击部署按钮,系统自动打包成可访问的Web服务,还能生成调用示例。:以前同步数据要写一堆IF-ELSE,先SELECT检查是否存在记录,再决定UPDATE还是INSERT。:单条语句完成"有则更新,无则插入"的操作,原子性执行避免竞态条件。的AI辅助开发,记得重点检查ON条件和字段映射,这两个地方最容易出问题。

CrystalwaveStag的博客 805

老版QQ原生表情gif动态

这是老版的QQ表情,不过全是动态的的,Windows照片查看器是不会动的,可以右击用浏览器打开查看,再说一遍是老版的,只是分享给宁愿用老版也要动态的人。

pscad IEEE标准系统搭建说明

pscad IEEE标准系统搭建说明,包含典型的IEEE 9节点、14节点、30节点、39节点和118节点系统。内含标准测试系统的原始数据和潮流结果。

merge into 和 update简单分析

merge into 和 update *update --创建学生表 create table student(id varchar2(9) not null primary key,name varchar2(40) not null,classnum number(2) not null,subject varchar2(40)); --创建教师表 create table teacher...

m0_38120426的博客 4304

RU DOS版、EFI版32bit/64bit BIOS常用工具

DOS版、EFI版的RU工具,可用来查看IO、MEM、PCI、SMBIOS等资源。亲测在EFI SHELL下可用。

oracle中merge into用法解析

merge into的形式: MERGEINTO [target-table] AUSING [source-tablesql] BON([conditional expression]and [...]...) WHENMATCHEDTHEN [UPDATEsql] WHENNOTMATCHEDTHEN [INSERTsql] 作用:判断B表和A表是否满足ON中条件,如果满足则用B表去更新A表,...

随风而逝的博客 1425

深度学习工具包 DeepLearningToolbox

深度学习工具包Deprecation notice.-----This toolbox is outdated and no longer maintained.There are much better tools available for deep learning than this toolbox, e.g. [Theano](http://deeplearning.net/software/theano/), [torch](http://torch.ch/) or [tensorflow](http://www.tensorflow.org/)I would suggest you use one of the tools mentioned above rather than use this toolbox.Best, Rasmus.DeepLearnToolbox================A Matlab toolbox for Deep Learning.Deep Learning is a new subfield of machine learning that focuses on learning deep hierarchical models of data.It is inspired by the human brain's apparent deep (layered, hierarchical) architecture.A good overview of the theory of Deep Learning theory is[Learning Deep Architectures for AI](http://www.iro.umontreal.ca/~bengioy/papers/ftml_book.pdf)For a more informal introduction, see the following videos by Geoffrey Hinton and Andrew Ng.* [The Next Generation of Neural Networks](http://www.youtube.com/watch?v=AyzOUbkUf3M) (Hinton, 2007)* [Recent Developments in Deep Learning](http://www.youtube.com/watch?v=VdIURAu1-aU) (Hinton, 2010)* [Unsupervised Feature Learning and Deep Learning](http://www.youtube.com/watch?v=ZmNOAtZIgIk) (Ng, 2011)If you use this toolbox in your research please cite [Prediction as a candidate for learning deep hierarchical models of data](http://www2.imm.dtu.dk/pubdb/views/publication_details.php?id=6284)```@MASTERSTHESIS\{IMM2012-06284, author = "R. B. Palm", title = "Prediction as a candidate for learning deep hierarchical models of data", year = "2012",}```Contact: rasmusbergpalm at gmail dot comDirectories included in the toolbox-----------------------------------`NN/` - A library for Feedforward Backpropagation Neural Networks`CNN/` - A library for Convolutional Neural Networks`DBN/` - A library for Deep Belief Networks`SAE/` - A library for Stacked Auto-Encoders`CAE/` - A library for Convolutional Auto-Encoders`util/` - Utility functions used by the libraries`data/` - Data used by the examples`tests/` - unit tests to verify toolbox is workingFor references on each library check REFS.mdSetup-----1. Download.2. addpath(genpath('DeepLearnToolbox'));Example: Deep Belief Network---------------------```matlabfunction test_example_DBNload mnist_uint8;train_x = double(train_x) / 255;test_x = double(test_x) / 255;train_y = double(train_y);test_y = double(test_y);%% ex1 train a 100 hidden unit RBM and visualize its weightsrand('state',0)dbn.sizes = [100];opts.numepochs = 1;opts.batchsize = 100;opts.momentum = 0;opts.alpha = 1;dbn = dbnsetup(dbn, train_x, opts);dbn = dbntrain(dbn, train_x, opts);figure; visualize(dbn.rbm{1}.W'); % Visualize the RBM weights%% ex2 train a 100-100 hidden unit DBN and use its weights to initialize a NNrand('state',0)%train dbndbn.sizes = [100 100];opts.numepochs = 1;opts.batchsize = 100;opts.momentum = 0;opts.alpha = 1;dbn = dbnsetup(dbn, train_x, opts);dbn = dbntrain(dbn, train_x, opts);%unfold dbn to nnnn = dbnunfoldtonn(dbn, 10);nn.activation_function = 'sigm';%train nnopts.numepochs = 1;opts.batchsize = 100;nn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.10, 'Too big error');```Example: Stacked Auto-Encoders---------------------```matlabfunction test_example_SAEload mnist_uint8;train_x = double(train_x)/255;test_x = double(test_x)/255;train_y = double(train_y);test_y = double(test_y);%% ex1 train a 100 hidden unit SDAE and use it to initialize a FFNN% Setup and train a stacked denoising autoencoder (SDAE)rand('state',0)sae = saesetup([784 100]);sae.ae{1}.activation_function = 'sigm';sae.ae{1}.learningRate = 1;sae.ae{1}.inputZeroMaskedFraction = 0.5;opts.numepochs = 1;opts.batchsize = 100;sae = saetrain(sae, train_x, opts);visualize(sae.ae{1}.W{1}(:,2:end)')% Use the SDAE to initialize a FFNNnn = nnsetup([784 100 10]);nn.activation_function = 'sigm';nn.learningRate = 1;nn.W{1} = sae.ae{1}.W{1};% Train the FFNNopts.numepochs = 1;opts.batchsize = 100;nn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.16, 'Too big error');```Example: Convolutional Neural Nets---------------------```matlabfunction test_example_CNNload mnist_uint8;train_x = double(reshape(train_x',28,28,60000))/255;test_x = double(reshape(test_x',28,28,10000))/255;train_y = double(train_y');test_y = double(test_y');%% ex1 Train a 6c-2s-12c-2s Convolutional neural network %will run 1 epoch in about 200 second and get around 11% error. %With 100 epochs you'll get around 1.2% errorrand('state',0)cnn.layers = { struct('type', 'i') %input layer struct('type', 'c', 'outputmaps', 6, 'kernelsize', 5) %convolution layer struct('type', 's', 'scale', 2) %sub sampling layer struct('type', 'c', 'outputmaps', 12, 'kernelsize', 5) %convolution layer struct('type', 's', 'scale', 2) %subsampling layer};cnn = cnnsetup(cnn, train_x, train_y);opts.alpha = 1;opts.batchsize = 50;opts.numepochs = 1;cnn = cnntrain(cnn, train_x, train_y, opts);[er, bad] = cnntest(cnn, test_x, test_y);%plot mean squared errorfigure; plot(cnn.rL);assert(er<0.12, 'Too big error');```Example: Neural Networks---------------------```matlabfunction test_example_NNload mnist_uint8;train_x = double(train_x) / 255;test_x = double(test_x) / 255;train_y = double(train_y);test_y = double(test_y);% normalize[train_x, mu, sigma] = zscore(train_x);test_x = normalize(test_x, mu, sigma);%% ex1 vanilla neural netrand('state',0)nn = nnsetup([784 100 10]);opts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samples[nn, L] = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.08, 'Too big error');%% ex2 neural net with L2 weight decayrand('state',0)nn = nnsetup([784 100 10]);nn.weightPenaltyL2 = 1e-4; % L2 weight decayopts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samplesnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex3 neural net with dropoutrand('state',0)nn = nnsetup([784 100 10]);nn.dropoutFraction = 0.5; % Dropout fraction opts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samplesnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex4 neural net with sigmoid activation functionrand('state',0)nn = nnsetup([784 100 10]);nn.activation_function = 'sigm'; % Sigmoid activation functionnn.learningRate = 1; % Sigm require a lower learning rateopts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samplesnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex5 plotting functionalityrand('state',0)nn = nnsetup([784 20 10]);opts.numepochs = 5; % Number of full sweeps through datann.output = 'softmax'; % use softmax outputopts.batchsize = 1000; % Take a mean gradient step over this many samplesopts.plot = 1; % enable plottingnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex6 neural net with sigmoid activation and plotting of validation and training error% split training data into training and validation datavx = train_x(1:10000,:);tx = train_x(10001:end,:);vy = train_y(1:10000,:);ty = train_y(10001:end,:);rand('state',0)nn = nnsetup([784 20 10]); nn.output = 'softmax'; % use softmax outputopts.numepochs = 5; % Number of full sweeps through dataopts.batchsize = 1000; % Take a mean gradient step over this many samplesopts.plot = 1; % enable plottingnn = nntrain(nn, tx, ty, opts, vx, vy); % nntrain takes validation set as last two arguments (optionally)[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');```[![Bitdeli Badge](https://d2weczhvl823v0.cloudfront.net/rasmusbergpalm/deeplearntoolbox/trend.png)](https://bitdeli.com/free "Bitdeli Badge")

Oracle MERGE INTO实战:如何用一条SQL搞定员工数据同步(附完整案例)

本文深入解析Oracle MERGE INTO语句的高级语法与应用,通过员工数据同步的完整实战案例,展示如何用一条SQL实现高效的‘更新或插入’操作。文章对比了传统方式的弊端,详细拆解了MERGE INTO的核心语法、使用子查询作为数据源、处理复杂业务规则及性能优化技巧,帮助开发者从根本上提升数据同步的效率和可靠性。

docker7nomad的博客 703

电商库存同步实战:Oracle MERGE INTO典型应用

电商库存同步主要面临两个问题:一是需要根据销售记录实时更新库存数量,二是当库存低于阈值时要标记预警状态。每天都会有大量的商品销售数据需要同步到库存表中,同时还需要根据库存情况触发预警。通过这个案例可以看出,Oracle的MERGE INTO在批量数据同步场景中非常高效。特别是电商这种需要频繁更新数据的业务,合理使用MERGE可以大幅提升系统性能。上尝试了类似的功能实现,发现它的一键部署特别方便,不用自己搭建Oracle环境就能测试SQL效果。销售记录表每天会产生大量数据,而库存表需要实时反映最新库存情况。

AgatePanther34的博客 904

告别多次查询:MERGE INTO如何将操作效率提升300%

MERGE INTO是Oracle中一个被低估的高效特性,特别适合需要"有则更新,无则插入"的场景。通过这次测试,我深刻体会到:- 一条优化过的SQL抵得上十段代码- 数据库原生特性往往有惊喜- 性能优化要从设计阶段开始考虑如果你也在处理类似的数据同步需求,强烈建议试试MERGE INTO语句,配合InsCode(快马)平台的便捷环境,开发效率会提升不少。

SnowflakeJaguar14的博客 940

Merge into的使用 之 Where 条件

Merge是一个非常有用的功能,类似于Mysql里的insert into on duplicate key. Oracle在9i引入了merge命令, 通过这个merge你能够在一个SQL语句中对一个表同时执行inserts和updates操作. 当然是update还是insert是依据于你的指定的条件判断的,Merge into可以实现用B表来更新A表数据,如果A表中没有,则把B表的数据...

s_xiaoqi的博客 2万+

Oracle中merge into的使用

引言    这篇文章不错,最后的方法解决了我的一个问题。原来使用H2数据库,使用Merge into,能自动实现更新或插入,到了Oracle的merge into,用起来不一样,同样的语句,在两个库中不是解决一个问题的。     Oracle中该命令使用一条语句从一个或者多个数据源中完成对表的更新和插入数据. ORACLE 9i 中,使用此命令必须同时指定UPDATE 和INSERT 关键词,OR...

liuyongfang0211的博客 286

oracle数据库中,merge into 语句的功能与使用场景

是ORACLE数据库 SQL 中的一种数据操作语句,它结合了 INSERT、UPDATE 和 DELETE 操作的功能,。

encoding-console的博客 1383

oracle merge into用法

在平时更新数据时,经常有这样一种更新,即将目标表中的数据与源表对比,如果存在记录,则根据源表中的值更新目标表中的数据,如果不存在的话,则新增入目标表中。我们当然可以使用两条语句来处理这类数据。但这其中有可能会出现异常。因此,Oracle在9i版本新增了MERGE语句,来合并UPDATE和INSERT语句。 该语句可以在同一语句中执行两步操作,可以减少执行多条insert 和update语句。m

linghao00的专栏 1454

Oracle 批量更新 中merge into的使用

http://blog.youkuaiyun.com/yuzhic/article/details/1896878 http://blog.youkuaiyun.com/macle2010/article/details/5980965   该命令使用一条语句从一个或者多个数据源中完成对表的更新和插入数据. ORACLE 9i 中,使用此命令必须同时指定UPDATE 和INSERT 关键词,ORACLE 10g ...

我爱技术男-江龙 1416
上一篇: Navicat Premium 16高效操作:提升数据库管理速度的快捷键秘籍
下一篇: VSCode中LaTeX Workshop插件的高级配置与优化
github5actions
博客等级 码龄1天 0粉丝 1824原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符  | 博主筛选后可见
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值