当前位置: 首页 > news >正文

Oracle LOB使用入门和简单使用,提供学习用的测试用例!

Oracle LOB字段使用方法与数据泵迁移实战指南

Oracle数据库中的LOB(Large Object)字段是存储大型非结构化数据的理想选择,支持高达4GB的文本、图像、音频、视频等数据存储。本问简单介绍创建含LOB/CLOB字段的表结构、批量插入10万行数据、拆分LOB表结构,并提供验证数据完整性的测试用例,适合复习或者学习新知识点用。

一、创建含LOB/CLOB字段的表结构

创建含LOB字段的表时,应根据业务需求选择适当的LOB类型,并合理配置存储参数以优化性能。对于大型文本数据,CLOB是最常用的选择;对于二进制数据,BLOB更为合适。以下是创建含CLOB字段的表的示例,采用SecureFiles存储方式并优化存储参数:

-- 创建专用表空间用于存储LOB数据
sqlplus / as sysdba
CREATE TABLESPACE lob_tbs
DATAFILE '/oradata/ora11g/lob_tbs01.dbf' SIZE 100M AUTOEXTEND ON MAXSIZE UNLIMITED
LOGGINGExtent Management LocalSegment Space Management Auto;-- 创建含CLOB字段的表,使用SecureFiles存储并优化参数
CREATE TABLE lob_table (id NUMBER PRIMARY KEY,text_data CLOB,binary_data BLOB,created_at DATE DEFAULT SYSDATE
)
TABLESPACE users
LOB (text_data) STORE AS SECUREFILE (TABLESPACE lob_tbsENABLE STORAGE IN ROWCHUNK 8192PCTVERSION 5COMPRESS HIGHDEDUPLICATENOCACHELOGGING
)
LOB (binary_data) STORE AS SECUREFILE (TABLESPACE lob_tbsENABLE STORAGE IN ROWCHUNK 8192PCTVERSION 5COMPRESS HIGHDEDUPLICATENOCACHELOGGING
);

关键参数解析

  1. SecureFiles:Oracle 11g引入的新存储方式,相比BasicFile提供了更好的性能和更多高级功能
  2. TABLESPACE lob_tbs:将LOB数据单独存储到专用表空间,避免与常规表数据竞争I/O资源
  3. ENABLE STORAGE IN ROW:允许小于4KB的LOB值存储在行内,提升小数据访问效率
  4. CHUNK 8192:设置为8KB(与数据库块大小一致),避免存储碎片
  5. PCTVERSION 5:将版本空间比例从默认10%降至5%,减少空间浪费
  6. COMPRESS HIGH:启用高级压缩,可节省约40-60%的存储空间
  7. DEDUPLICATE:启用去重功能,自动检测并合并重复数据,进一步节省存储空间
  8. NOCACHE:对于只读或低频更新的LOB数据,禁用缓存可减少内存占用
  9. LOGGING:启用日志记录,确保数据完整性和可恢复性

二、批量插入10万行测试数据

对于大型LOB数据的批量插入,直接逐行插入效率低下,应采用PL/SQL批量操作方法,结合临时LOB和分批次提交机制,以提高插入效率。

-- 创建存储过程,批量插入10万行数据
CREATE OR REPLACE PROCEDURE insert_lob_data(p_rows IN NUMBER := 100000) IS-- 定义用于批量插入的集合类型TYPE t_ids IS TABLE OF NUMBER;TYPE t_clobs IS TABLE OF CLOB;v_ids t_ids;v_clobs t_clobs;v_buffer VARCHAR2(32767);v_max_length NUMBER := 5000; -- 每个CLOB数据的平均长度v_batch_size NUMBER := 1000; -- 每批插入的行数v_start_time TIMESTAMP := SYSTIMESTAMP;v_start NUMBER;v_end   NUMBER;v_current_row NUMBER := 1;
BEGIN-- 使用 EXECUTE IMMEDIATE 执行 DDLEXECUTE IMMEDIATE 'ALTER TABLE lob_table NOLOGGING';DBMS_OUTPUT.PUT_LINE('Generating LOB data and IDs for batches...');-- 生成随机数据缓冲区(使用英文字符避免乱码)v_buffer := DBMS_RANDOM.STRING('x', 32767); -- 注意:'x' 表示大小写字母+数字-- 分批次处理,避免一次性将所有数据加载到内存FOR batch_num IN 1..CEIL(p_rows / v_batch_size) LOOPv_start := (batch_num - 1) * v_batch_size + 1;v_end   := LEAST(batch_num * v_batch_size, p_rows);-- 初始化当前批次的集合v_ids := t_ids();v_clobs := t_clobs();-- 为当前批次生成数据FOR i IN v_start..v_end LOOP-- 扩展集合大小v_ids.EXTEND;v_clobs.EXTEND;-- 设置IDv_ids(v_ids.LAST) := i;-- 创建并填充临时CLOBDBMS_LOB.CREATETEMPORARY(v_clobs(v_clobs.LAST), TRUE);DECLAREv_written NUMBER := 0;v_chunk   NUMBER := 32767;v_to_write NUMBER;v_current_buffer VARCHAR2(32767);BEGINWHILE v_written < v_max_length LOOPv_current_buffer := SUBSTR(v_buffer, 1, LEAST(32767, v_max_length - v_written));v_to_write := LENGTH(v_current_buffer);DBMS_LOB.WRITEAPPEND(v_clobs(v_clobs.LAST), v_to_write, v_current_buffer);v_written := v_written + v_to_write;END LOOP;END;END LOOP;DBMS_OUTPUT.PUT_LINE('Inserting batch ' || batch_num || ' (' || v_start || '-' || v_end || ')...');-- 使用 FORALL 批量插入当前批次的数据FORALL j IN INDICES OF v_idsINSERT INTO lob_table (id, text_data)VALUES (v_ids(j), v_clobs(j));COMMIT;DBMS_OUTPUT.PUT_LINE('Batch ' || batch_num || ' committed.');-- 释放当前批次的临时LOB资源FOR k IN 1..v_clobs.COUNT LOOPIF DBMS_LOB.ISTEMPORARY(v_clobs(k)) = 1 THENDBMS_LOB.FREETEMPORARY(v_clobs(k));END IF;END LOOP;END LOOP;-- 插入完成后恢复 LOGGING 模式EXECUTE IMMEDIATE 'ALTER TABLE lob_table LOGGING';-- 输出统计信息DBMS_OUTPUT.PUT_LINE('Total rows inserted: ' || p_rows);DBMS_OUTPUT.PUT_LINE('Time taken: ' || TO_CHAR(SYSTIMESTAMP - v_start_time));EXCEPTIONWHEN OTHERS THEN-- 异常处理:尝试释放已创建的临时LOBIF v_clobs IS NOT NULL THENFOR k IN 1..v_clobs.COUNT LOOPIF v_clobs.EXISTS(k) AND DBMS_LOB.ISTEMPORARY(v_clobs(k)) = 1 THENDBMS_LOB.FREETEMPORARY(v_clobs(k));END IF;END LOOP;END IF;-- 回滚事务ROLLBACK;-- 重新抛出异常RAISE;
END;
/select bytes/1024/1024 size_mb from dba_segments where segment_name = upper('lob_table');SIZE_MB
----------.0625

批量插入优化策略

  1. 临时LOB:使用DBMS_LOB.Createtemporary创建临时LOB对象,减少磁盘I/O
  2. 绑定变量:避免在SQL语句中直接拼接LOB值,使用绑定变量提高效率
  3. 分批次提交:每1000行提交一次事务,平衡锁表时间和日志管理
  4. NOLOGGING模式:在批量插入前启用NOLOGGING模式,可提高插入速度约3-5倍
  5. 并行执行:对于超大规模数据,可考虑使用PARALLEL提示并行插入

执行上述存储过程插入10万行数据:

SET SERVEROUTPUT ON;
BEGINinsert_lob_data(100000); -- 插入10万行
END;
/-- 插入数据过程中,表一直在变大
select bytes/1024/1024 size_mb from dba_segments where segment_name = upper('lob_table');SIZE_MB
----------663SQL> /SIZE_MB
----------671

插入性能优化

对于超大规模数据插入,建议采用以下优化措施:

  • 使用FORALL批量插入代替循环逐行插入
  • 启用COMMIT前的NOLOGGING模式,减少重做日志开销
  • 调整PCTVERSION参数,减少版本空间占用
  • 考虑使用外部表或SQL*Loader进行超大规模数据导入

三、拆分LOB表结构

为提高大型LOB表的查询性能和管理便利性,可采用表空间分离或分区表策略拆分LOB数据。
表空间分离是最简单有效的方式,将LOB数据存储到独立表空间,避免与常规表数据竞争I/O资源。

-- 创建专用表空间用于存储拆分后的LOB数据
CREATE TABLESPACE lob_tbs_split
DATAFILE '/oradata/ora11g/lob_tbs_split01.dbf' SIZE 100M AUTOEXTEND ON MAXSIZE UNLIMITED
LOGGINGExtent Management LocalSegment Space Management Auto;-- 将LOB数据移动到新表空间
ALTER TABLE lob_table MOVE LOB (text_data) STORE AS (TABLESPACE lob_tbs_split);
ALTER TABLE lob_table MOVE LOB (binary_data) STORE AS (TABLESPACE lob_tbs_split);这些命令只是移动了LOB列的存储段(LOB Segment)到 lob_tbs_split 表空间,但并没有移动表本身的数据段(Table Segment)。因此:
表的数据段(存储 id, created_at 等非LOB列)仍然在 USERS 表空间
LOB的数据段(存储 text_data, binary_data 列)已经移动到 lob_tbs_split 表空间set lin 100
col SEGMENT_NAME for a30
col TABLESPACE_NAME for a30
SELECT SEGMENT_NAME,SEGMENT_TYPE,TABLESPACE_NAME
FROM DBA_SEGMENTS 
WHERE SEGMENT_NAME IN (SELECT SEGMENT_NAME FROM USER_LOBS WHERE TABLE_NAME = 'LOB_TABLE'
);
SEGMENT_NAME                   SEGMENT_TYPE                         TABLESPACE_NAME
------------------------------ ------------------------------------ ------------------------------
SYS_LOB0000112369C00002$$      LOBSEGMENT                           LOB_TBS_SPLIT
SYS_LOB0000112369C00003$$      LOBSEGMENT                           LOB_TBS_SPLIT
http://www.dtcms.com/a/469269.html

相关文章:

  • Java版旅游系统/文旅系统/旅游助手/旅游攻略/公众号/小程序/app全套源码
  • 线程2---javaEE(校招)
  • [创业之路-687]:华为“1+8+N”战略以及其背后的技术栈、商业逻辑。
  • 基于大语言模型(LLM)的城市时间、空间与情感交织分析:面向智能城市的情感动态预测与空间优化
  • 眼控交互:ErgoLAB新一代人机交互方式
  • 数字货币众筹网站开发如何做高网站的浏览量
  • 网站服务器频繁掉线的主要原因是什么
  • codeigniter换服务器之后,会员登录之后又跳回登录页面的解决方法
  • VS Code 的 SSH 密钥,并将其安全地添加到服务器
  • 香港服务器速度快慢受何影响?
  • 服务器相关:什么是 alios. centos. cuda. cuda tookit. gcc. cudann. pytorch.
  • K8S(五)—— K8s中YAML文件全方位解析:语法、案例、Port详解与快速编写技巧
  • 企业网站注销流程做企业网站需要服务器么
  • k8s存储juicefs简介
  • Ansible模块介绍(接上段)
  • 河南省建设厅网站官网重庆seo务
  • 【开题答辩全过程】以 北京房屋租赁数据分析与可视化为例,包含答辩的问题和答案
  • 什么身一什么网站建设网站开发毕设任务书
  • 【八股消消乐】手撕分布式协议和算法(基础篇)
  • Databend 九月月报:自增列 AUTOINCREMENT 与行级安全
  • Zenlayer 推出分布式推理平台,加速 AI 创新全球落地
  • 01-iptables防火墙安全
  • Docker存储技术全解析:分层与持久化
  • 分布式专题——39 RocketMQ客户端编程模型
  • 物联网二级平台设计与实现:从Home Assistant到JetLinks的设备协同架构实践
  • 分布式文件存储 RPC 服务实现
  • 在哪些软件上建设网站市场营销方案怎么做
  • 《小小梦魇3》今日发售!用UU远程手机躺玩通关
  • Jenkins Pipeline post指令详解
  • 系列文章<一>(从LED显示问题到非LED领域影像画质优化:揭秘跨领域的核心技术):从LED冬奥会、奥运会及春晚等大屏,到手机小屏,快来挖一挖里面都有什么