【Oracle篇】跨字符集迁移:基于数据泵的ZHS16GBK转AL32UTF8全流程迁移
💫《博主主页》:奈斯DB-CSDN博客
🔥《擅长领域》:擅长阿里云AnalyticDB for MySQL(分布式数据仓库)、Oracle、MySQL、Linux、prometheus监控;并对SQLserver、NoSQL(MongoDB)有了解
💖如果觉得文章对你有所帮助,欢迎点赞收藏加关注💖

最近公司某个项目组,因为业务扩展所以需要在数据库中存储越南语,当前这套Oracle实例由于当时在搭建时使用的是GBK字符集,所以存储越南语就会存在乱码,因为 ZHS16GBK字符集只对汉字、英文字符、数字,+-*/等进行了编码,没有对越南语进行编码所以存储越南语时就会有乱码 ;而AL32UTF8字符集,基本上对全世界的字符进行了编码存储,对于越南语而言支持所有带声调的越南文字符(ư, ơ, ế, ệ等)【AL32UTF8不仅仅可以存储越南语,还可以存储日文、韩文等等】 ,那么就需要将业务用户由ZHS16GBK字符集转成AL32UTF8。
小伙伴们都知道数据泵可以完成对全库、单个生产用户、生产表、某个表空间的迁移,这些都是难度比较小的操作,如果有一个场景因为业务扩展需要存储 日文、越南语 ,现在的Oracle字符集是ZHS16GBK,但是,需要将Oracle的字符集改成AL32UTF8去存储日文、越南语,那么又应该怎么办呢?
既然抛出了这个问题就要解决这个问题,我先给出答案——最安全的办法就是重建一个实例,然后修改char/varchar2数据类型的长度,最后通过expdp/impdp数据泵导入进去,当前数据库实例上有多个业务用户,好在只有这一个业务用户有迁移字符集的需求,那么本篇文章主要是通过数据泵完成对一个业务用户字符集的迁移,即使是全库用户都需要转换字符集也是一样的流程。那么带着这个问题,让我们开始今天的内容,通过expdp/impdp轻松完成某个生产用户从GBK到UTF8编码的迁移。
特别说明💥:本篇文章部分知识点均来源于 Oracle 公开可查的官方文档手册,并结合了我个人的理解和案例演示。如有冲突,请联系,会立即处理。转载请标明出处😄
官方文档对于字符集作用的介绍(Oracle 19c):
Choosing a Character Set
官方文档对于字符集迁移的介绍(Oracle 19c):
Character Set Migration
目录
源生产库(ZHS16GBK,实例liudbywcs,RAC环境)部分
目标库(AL32UTF8,实例baj,RAC环境)部分
验证数据部分
Oracle字符集的作用:
Oracle数据库中的字符集(Character Set)是数据库全球化支持(NLS)的核心组成部分,它的存在和设计源于计算机处理多语言文本的基本需求。以下是Oracle官方文档中阐述的字符集作用和存在原因:
字符编码映射
建立二进制数据与人类可读字符之间的对应关系
例如:在ZHS16GBK中
0xB0A1对应"啊",在AL32UTF8中0xE5958A对应同一个汉字数据存储规范
定义每个字符占用的存储空间(单字节/多字节)
例如:US7ASCII每个字符固定1字节,AL32UTF8中文常用字占3字节
排序与比较规则
决定
ORDER BY、WHERE条件比较等操作的排序规则不同字符集对相同字符的排序顺序可能不同
Oracle常用字符集:
1.US7ASCII - 基础ASCII字符集基本特性:
7位编码标准,共128个字符(0x00-0x7F)
不支持任何扩展字符
每个字符固定占用1字节存储空间
支持范围:
英文字母(A-Z, a-z)
数字(0-9)
基本标点符号和特殊字符(!@#$%^&*等)
控制字符(换行、回车等)
典型问题:
-- 尝试存储非ASCII字符会报错或显示为? INSERT INTO test VALUES ('中文'); -- 结果: ??适用场景:
纯英文应用系统
遗留系统维护
需要最小存储开销的环境
2. ZHS16GBK - 简体中文字符集
编码结构:
扩展GB2312标准,支持21003个汉字
双字节编码(0x8140-0xFEFE)
兼容ASCII(0x00-0x7F单字节)
字符范围:
简体中文(GB 18030-2000基本集)
常见繁体字
中文标点符号(全角)
部分日文假名和特殊符号
存储示例:
"中国" -> 0xD6D0 0xB9FA (2个双字节编码) "ABC" -> 0x41 0x42 0x43 (单字节ASCII兼容)局限性:
不支持越南语、泰语等东南亚文字
部分生僻字可能无法显示
3. JA16SJIS - 日文字符集
编码特点:
基于Shift-JIS编码标准
混合单字节(ASCII)和双字节编码
包含JIS X 0201和JIS X 0208字符集
字符组成:
全角假名(平假名、片假名)
日文汉字(常用约6000字)
半角假名和符号
英数字(半角/全角)
编码示例:
"日本語" -> 0x93FA 0x967B 0x8CEA (3个双字节编码) "ハンカク" -> 0xB1 0xB2 0xB3 0xB4 (半角假名)注意事项:
与EUC-JP编码不兼容
某些特殊符号可能显示异常
4. KO16KSC5601 - 韩文字符集
标准规范:
基于KS C 5601-1987标准
完全双字节编码(0xA1A1-0xFEFE)
包含2350个韩文音节和4888个汉字
字符构成:
韩文字母(谚文)
常用汉字
特殊符号和图形字符
编码特性:
"한국" -> 0xC7D1 0xB1B9 (2个双字节) "大韓民國" -> 0xB4EB 0xC7D1 0xB9DD 0xB0FA (4个双字节)使用限制:
不包含部分新造韩文字
汉字数量有限
5. AL32UTF8 - Unicode字符集
核心优势:
完整Unicode支持(最新版本)
可变长度编码(1-4字节/字符)
兼容所有语言字符
编码方式:
ASCII字符:1字节(0x00-0x7F)
欧洲文字:通常2字节(如é: 0xC3A9)
中文/日文/韩文:通常3字节(中: 0xE4B8AD)
特殊符号/罕见字:4字节
存储对比:
GBK中的"中国":4字节(D6D0 B9FA) UTF8中的"中国":6字节(E4B8AD E59BBD)关键特性:
-- 多语言混合存储示例 INSERT INTO multilingual VALUES ('中文Chinese日本語한국語ViệtNam');实施建议:
字段长度调整:VARCHAR2(100)可能需扩大
排序规则:使用NLS_SORT参数指定
性能考虑:索引大小可能增加
比较总结:
特性 US7ASCII ZHS16GBK JA16SJIS KO16KSC5601 AL32UTF8 编码范围 128字符 2.1万汉字 6千日文 7千韩文 全Unicode 存储效率 最高 高 中 高 可变 多语言支持 仅英文 中/英 日/英 韩/中/英 全球语言 字节/字符 1 1或2 1或2 2 1-4 推荐场景 纯英文 简体中文 日文系统 韩文系统 国际系统
迁移建议:从任何单语言字符集迁移到AL32UTF8时,需特别注意:
字段长度可能不足(UTF8通常需要更多空间)
应用程序可能需要调整字符处理逻辑
导出/导入时明确指定字符集转换
字符集存储数据相关参数:
SQL> show parameter NLS_LENGTH_SEMANTICSNLS_LENGTH_SEMANTICS:用于指定长度语义,有两个值BYTE、CHAR。mysql的字符集转换不同于oracle,因为oracle是字节byte所以涉及到列长度的转换,但mysql是存储是用char,所以不涉及到列的转换。但是Oracle可以通过NLS_LENGTH_SEMANTICS参数设置用BYTE还是CHAR存储数据,默认是BYTE字节存储。这个参数主要是针对char和varchar2这两种数据类型,数据存储是使用字节byte还是字符char设计的。对于NCHAR、NVARCHAR2、CLOB和NCLOB列始终基于char字符。
- BYTE:以字节的形式存储数据,默认值。gbk迁移到utf8就会涉及到char和varchar2数据类型的长度转换。
- CHAR:以字符的形式存储数据,gbk迁移到utf8不会涉及到长度转换。
注意:Oracle强烈建议不要在运行的实例中将参数设置为CHAR,因为可能导致许多现有安装脚本或者表数据意外地创建具有字符长度语义的列,从而导致运行时错误,包括缓冲区溢出。可以考虑在新实例中修改,新实例修改参考下面的案例一,修改长度语义只对后续手动创建的表生效,现有表还是原byte
首先了解为什么迁移字符集需要修改char/varchar2数据类型的长度,而不需要修改数值、日期等数据类型的长度。下面我们先看案例——汉字和字符在char/varchar2/nchar/nvarchar2数据类型中的占用的字节:
-
char(n)存放定长的字符串,最大存放2000 bytes
AMERICAN_AMERICA.ZHS16GBK(一个字符1字节,一个汉字为2字节)
SQL> create table liu_oracleoltp_ywcs_t1_gbk (name char(32)); ###创建字段为char32数据类型的liu_oracleoltp_ywcs_t1_gbk表,数据类型的字符串长度一般是16的倍数,例32,64,128等 SQL> show parameter NLS_LENGTH_SEMANTICS; ###首先确定存放字符的类型,默认是字节byte存储,有char、byte两个值。 SQL> insert into liu_oracleoltp_ywcs_t1_gbk values('Oracle'); SQL> insert into liu_oracleoltp_ywcs_t1_gbk values('甲骨文');SQL> select name,dump(name) from liu_oracleoltp_ywcs_t1_gbk; ###dump为展现这个行(name)的详细内容 ###插入数据的详细内容,数字代表字码,79代表字母O,空格用32代码表示
AMERICAN_AMERICA.AL32UTF8(一个字符1字节,一个汉字为3字节)
SQL> create table liu_oracleoltp_ywcs_t2_utf8 (name char(32)); ###创建字段为char32数据类型的liu_oracleoltp_ywcs_t2_utf8表,数据类型的字符串长度一般是16的倍数,例32,64,128等 SQL> show parameter NLS_LENGTH_SEMANTICS; ###首先确定存放字符的类型,默认是字节byte存储,有char、byte两个值。 SQL> insert into liu_oracleoltp_ywcs_t2_utf8 values('Oracle'); SQL> insert into liu_oracleoltp_ywcs_t2_utf8 values('甲骨文');SQL> select name,dump(name) from liu_oracleoltp_ywcs_t2_utf8; ###dump为展现这个行(name)的详细内容 ###插入数据的详细内容,数字代表字码,79代表字母O,空格用32代码表示
-
varchar2(n):存放可变长长度的字符集,最大可以存放4000 bytes
AMERICAN_AMERICA.ZHS16GBK(一个字符1字节,一个汉字为2字节)
SQL> create table liu_oracleoltp_ywcs_t3_gbk (name varchar2(16)); SQL> show parameter NLS_LENGTH_SEMANTICS; ###首先确定存放字符的类型,默认是字节byte存储,有char、byte两个值。 SQL> insert into liu_oracleoltp_ywcs_t3_gbk(name) values('Oracle'); SQL> insert into liu_oracleoltp_ywcs_t3_gbk(name) values('甲骨文');SQL> select name,dump(name) from liu_oracleoltp_ywcs_t3_gbk; ###1、存放了‘Oracle’的6个字符,实际存放数据库中,就只占用了6个(‘Oracle’),其余的剩下的字符就被回收了。 ###2、如果插入数据是固定长度的,比如手机号码(11位)、身份证号(18位),则应当使用char来存放,这样的好处是查询与检索速度较快。原因为查询char类型的字段时,作为整体进行查询,而varchar2是一个个数据进行比对的。而如果存放的字符串的长度不固定,则建议使用varchar2(size)
AMERICAN_AMERICA.AL32UTF8(一个字符1字节,一个汉字为3字节)
SQL> create table liu_oracleoltp_ywcs_t4_utf8 (name varchar2(16)); SQL> show parameter NLS_LENGTH_SEMANTICS; ###首先确定存放字符的类型,默认是字节byte存储,有char、byte两个值。 SQL> insert into liu_oracleoltp_ywcs_t4_utf8(name) values('Oracle'); SQL> insert into liu_oracleoltp_ywcs_t4_utf8(name) values('甲骨文');SQL> select name,dump(name) from liu_oracleoltp_ywcs_t4_utf8; ###1、存放了‘Oracle’的6个字符,实际存放数据库中,就只占用了6个(‘Oracle’),其余的剩下的字符就被回收了。 ###2、如果插入数据是固定长度的,比如手机号码(11位)、身份证号(18位),则应当使用char来存放,这样的好处是查询与检索速度较快。原因为查询char类型的字段时,作为整体进行查询,而varchar2是一个个数据进行比对的。而如果存放的字符串的长度不固定,则建议使用varchar2(size)
-
nchar(n):根据字符集而定的固定长度字符集,nchar(n)最大存放2000 bytes
AMERICAN_AMERICA.ZHS16GBK(一个字符2字节,一个汉字为2字节)
SQL> create table liu_oracleoltp_ywcs_t5_gbk (name nchar(16)); SQL> show parameter NLS_LENGTH_SEMANTICS; ###首先确定存放字符的类型,默认是字节byte存储,有char、byte两个值。 SQL> insert into liu_oracleoltp_ywcs_t5_gbk(name) values('Oracle'); SQL> insert into liu_oracleoltp_ywcs_t5_gbk(name) values('甲骨文');SQL> select name,dump(name) from liu_oracleoltp_ywcs_t5_gbk;
AMERICAN_AMERICA.AL32UTF8(一个字符2字节,一个汉字为2字节)
SQL> create table liu_oracleoltp_ywcs_t7_utf8 (name nchar(16)); SQL> show parameter NLS_LENGTH_SEMANTICS; ###首先确定存放字符的类型,默认是字节byte存储,有char、byte两个值。 SQL> insert into liu_oracleoltp_ywcs_t7_utf8(name) values('Oracle'); SQL> insert into liu_oracleoltp_ywcs_t7_utf8(name) values('甲骨文');SQL> select name,dump(name) from liu_oracleoltp_ywcs_t7_utf8;
-
nvarchar2(n):根据字符集而定的固定长度字符集,nvarchar2(n)最大存放4000 bytes。
AMERICAN_AMERICA.ZHS16GBK(一个字符2字节,一个汉字为2字节)
SQL> create table liu_oracleoltp_ywcs_t6_gbk (name nvarchar2(16)); SQL> show parameter NLS_LENGTH_SEMANTICS; ###首先确定存放字符的类型,默认是字节byte存储,有char、byte两个值。 SQL> insert into liu_oracleoltp_ywcs_t6_gbk(name) values('Oracle'); SQL> insert into liu_oracleoltp_ywcs_t6_gbk(name) values('甲骨文');SQL> select name,dump(name) from liu_oracleoltp_ywcs_t6_gbk;
AMERICAN_AMERICA.AL32UTF8(一个字符2字节,一个汉字为2字节)
SQL> create table liu_oracleoltp_ywcs_t8_utf8 (name nvarchar2(16)); SQL> show parameter NLS_LENGTH_SEMANTICS; ###首先确定存放字符的类型,默认是字节byte存储,有char、byte两个值。 SQL> insert into liu_oracleoltp_ywcs_t8_utf8(name) values('Oracle'); SQL> insert into liu_oracleoltp_ywcs_t8_utf8(name) values('甲骨文');SQL> select name,dump(name) from liu_oracleoltp_ywcs_t8_utf8;
那么现在明白了为什么修改字符集时需要增加 char/varchar2数据类型 长度了吧!对于NCHAR、NVARCHAR2、CLOB和NCLOB列始终基于char字符,CLOB和NCLOB大字段的数据类型一般是不会指定长度的,所以也就不会涉及到长度的增加了,所以这里我就不演示了。
那么总结一下:
Oracle字符集的修改不要在现有的实例上直接去修改,因为oracle默认是 字节byte 所以涉及到列长度的转换,转换涉及到 char和varchar2 两种数据类型,其他数据类型不涉及到转换,也有通过 在线修改单机或者rac的字符集 ,但是会有很大的风险,所以通过expdp/impdp数据泵是最有效的方案。
源生产库(ZHS16GBK,实例liudbywcs,RAC环境)部分
1、字符集存储数据参数
SQL> show parameter NLS_LENGTH_SEMANTICS;
###BYTE:以字节的形式存储数据,默认值。gbk迁移到utf8就会涉及到char和varchar2数据类型的长度转换。

2、创建数据泵的dmp文件存放目录
[root@rac1 ~]# mkdir /liu [root@rac1 ~]# chown oracle:oinstall /liu ###文件liu(路径/liu)在/dev/sdb3下挂载,将文件的所属用户和目录改为oracle:oinstall[root@rac1 ~]# sqlplus / as sysdba SYS@orcl> create directory BACKUP20200328 as '/liu'; SYS@orcl> grant all on directory BACKUP20200328 to system ; ###创建数据泵的转储路径(在使用expdp时,指定到liu目录时,数据文件就会生成在/liu路径下)。赋予给所有用户目录liu的所有执行权限,为了以后普通用户使用expdp时有权限将dmp数据文件导入到/liu下。
3、导出的数据库为ZHS16GBK,只导出生产baj这个用户
[oracle@rac1 ~]$ export ORACLE_SID=liudbywcs1
[oracle@rac1 ~]$ echo $ORACLE_SID[oracle@rac1 ~]$ expdp baj/baj directory=BACKUP20200328 dumpfile=expdp_liudbywcs_baj_%U.dmp logfile=expdp_orcl_baj.log schemas=baj parallel=4 cluster=n
4、生成生产库的业务表空间SQL语句:
ps:排查掉SYSAUX、SYSTEM、TEMP、UNDOTBS1、USERS这些系统表空间的创建
SQL> set linesize 500 set pagesize 99col file_name for a70 col file_id for 9999999 col status for a10 col ts_name for a25 col cur_mb for 99999 select status, file_id, file_name, tablespace_name ts_name,blocks/128 tolal_mb, maxblocks/128 max_mb,AUTOEXTENSIBLE,status,online_status from dba_data_files order by file_name;SQL> SET LONG 2000000 PAGESIZE 0 head off verify off feedback off linesize 180 SQL> select dbms_metadata.get_ddl('USER','BAJ') from dual; ###查看创建用户的语句,需要确定默认的表空间和默认的临时表空间
SQL> select dbms_metadata.get_ddl('TABLESPACE','NNC_DATA01') from dual; ###查看创建表空间的语句
SQL> select dbms_metadata.get_ddl('TABLESPACE','NNC_INDEX01') from dual;
目标库(AL32UTF8,实例baj,RAC环境)部分
1、生产baj用户导入前需要注意的事情:
1)关注归档目录,定时进行删除,避免空间耗尽。可以考虑先关闭归档
2)baj数据量有500G以上,导入过程中undo和temp占用很多,适当扩容。
博主在实际迁移过程中Undo表空间给7个,总大小210G,并且减少undo_retention为300秒
Temp表空间给3个,总大小90G
3)数据文件看情况增加
2、在服务器上创建一个AL32UTF8字符集的实例baj
这里就不演示安装实例过程中,需要主要的是字符集需要为AL32UTF8
3、确认字符集调整undo保留时间
[oracle@rac1 ~]# export ORACLE_SID=baj1
[oracle@rac1 ~]# echo $ORACLE_SIDSQL> alter system set undo_retention=300 scope=both sid='*'; --导入完成之后修改回来SQL> select * from nls_database_parameters;
SQL> select * from v$nls_parameters;
SQL> select userenv('language') from dual ;
4、创建表空间
SQL>
set linesize 500
set pagesize 99
col file_name for a70
col file_id for 9999999
col status for a10
col ts_name for a25
col cur_mb for 99999
select status, file_id, file_name, tablespace_name ts_name,blocks/128 tolal_mb, maxblocks/128 max_mb,AUTOEXTENSIBLE,status,online_status from dba_data_files order by file_name;alter tablespace UNDOTBS1 add datafile '+DATADG' size 31G autoextend on;
alter tablespace UNDOTBS1 add datafile '+DATADG' size 31G autoextend on;
alter tablespace UNDOTBS1 add datafile '+DATADG' size 31G autoextend on;
alter tablespace UNDOTBS1 add datafile '+DATADG' size 31G autoextend on;
alter tablespace UNDOTBS1 add datafile '+DATADG' size 31G autoextend on;alter tablespace UNDOTBS2 add datafile '+DATADG' size 31G autoextend on;
alter tablespace UNDOTBS2 add datafile '+DATADG' size 31G autoextend on;
alter tablespace UNDOTBS2 add datafile '+DATADG' size 31G autoextend on;
alter tablespace UNDOTBS2 add datafile '+DATADG' size 31G autoextend on;
alter tablespace UNDOTBS2 add datafile '+DATADG' size 31G autoextend on;alter tablespace temp add tempfile '+DATADG' size 31G autoextend on;
alter tablespace temp add tempfile '+DATADG' size 31G autoextend on; CREATE TABLESPACE "NNC_DATA01" DATAFILE
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 5G autoextend on,
'+DATADG' SIZE 1G autoextend on,
'+DATADG' SIZE 1G autoextend on,
'+DATADG' SIZE 1G autoextend on,
'+DATADG' SIZE 1G autoextend on,
'+DATADG' SIZE 1G autoextend onLOGGING ONLINE PERMANENT BLOCKSIZE 8192EXTENT MANAGEMENT LOCAL AUTOALLOCATE DEFAULTNOCOMPRESS SEGMENT SPACE MANAGEMENT AUTO;
CREATE TABLESPACE "NNC_INDEX01" DATAFILE
'+DATADG' SIZE 1G autoextend on,
'+DATADG' SIZE 1G autoextend on,
'+DATADG' SIZE 1G autoextend on,
'+DATADG' SIZE 1G autoextend on,
'+DATADG' SIZE 1G autoextend on,
'+DATADG' SIZE 1G autoextend on,
'+DATADG' SIZE 1G autoextend on,
'+DATADG' SIZE 1G autoextend onLOGGING ONLINE PERMANENT BLOCKSIZE 8192EXTENT MANAGEMENT LOCAL AUTOALLOCATE DEFAULTNOCOMPRESS SEGMENT SPACE MANAGEMENT AUTO;CREATE TABLESPACE "NNC_INDEX01" DATAFILE
'+DATADG' SIZE 1G autoextend on,
'+DATADG' SIZE 1G autoextend on,
'+DATADG' SIZE 1G autoextend on,
'+DATADG' SIZE 1G autoextend on,
'+DATADG' SIZE 1G autoextend on,
'+DATADG' SIZE 1G autoextend on,
'+DATADG' SIZE 1G autoextend on,
'+DATADG' SIZE 1G autoextend onLOGGING ONLINE PERMANENT BLOCKSIZE 8192EXTENT MANAGEMENT LOCAL AUTOALLOCATE DEFAULTNOCOMPRESS SEGMENT SPACE MANAGEMENT AUTO;
5、创建存放DMP文件夹的引用地址
SQL> create directory baj_dir as '/home/oracle/backup20200328';
SQL> grant all on directory baj_dir to system;
6、linux下使用impdp工具导入(只是导入对象):
[oracle@rac1 ~]# export ORACLE_SID=baj1
[oracle@rac1 ~]# echo $ORACLE_SID[oracle@rac1 ~]# impdp system/oracle directory=baj_dir dumpfile=expdp_orcl_baj_01.dmp,expdp_orcl_baj_02.dmp,expdp_orcl_baj_03.dmp,expdp_orcl_baj_04.dmp logfile=impdp_baj_baj_metadata_only.log schemas=baj parallel=8 CONTENT=metadata_only table_exists_action=append cluster=n
####impdp导入之前,需要在目标数据库上创建相应表空间对象即可;而对于imp导入时需要在目标数据库上创建相应的用户、权限、表空间等对象。
7、旧库迁移到新库,旧库编码是GBK,新库是UTF-8,一个汉字GBK占2个字节,UTF-8占三个字节,故对varchar2和char类型字段扩容二分之一
注意:有些业务表是定长char数据类型,但是内容只有字符,没有汉字,如果统一进行扩容的话可能会影响程序对char数据类型的判断,所以对于char数据类型按照要求扩长或者不扩长,哪些char必须要扩容只有在导入的时候报错了再考虑对char进行扩容。
[oracle@rac1 ~]# sqlplus baj/123456 ###连接到baj用户执行下面操作
扩展char小于1300的SQL语句:
SQL> set pagesize 0; SQL> spool /home/oracle/char1.sqlSELECT 'alter table ' || t_column.table_name || ' modify ' ||t_column.column_name || ' char(' || (t_column.data_length + ceil(t_column.data_length * 0.5)) || ');' AS alter_sqlstrFROM user_tab_columns t_column, user_tables t_tablesWHERE t_column.table_name = t_tables.table_nameAND t_column.data_length <= 1300AND t_column.data_type = 'CHAR'; SQL> spool off
扩展char大于1300且小于2000的SQL语句:
SQL> set pagesize 0; SQL> spool /home/oracle/char2.sqlSELECT 'alter table ' || t_column.table_name || ' modify ' ||t_column.column_name || ' char(2000);' AS alter_sqlstrFROM user_tab_columns t_column, user_tables t_tablesWHERE t_column.table_name = t_tables.table_nameAND t_column.data_length > 1300AND t_column.data_length < 2000AND t_column.data_type = 'CHAR'; SQL> spool off
扩展varchar2大于2600且小于4000的SQL语句:
SQL> set pagesize 0; SQL> spool /home/oracle/char3.sqlSELECT 'alter table ' || t_column.table_name || ' modify ' ||t_column.column_name || ' varchar2(4000);' AS alter_sqlstrFROM user_tab_columns t_column, user_tables t_tablesWHERE t_column.table_name = t_tables.table_nameAND t_column.data_length > 2600AND t_column.data_length < 4000AND t_column.data_type = 'VARCHAR2'; SQL> spool off
扩展varchar2小于2600的SQL语句:
SQL> set pagesize 0; SQL> spool /home/oracle/char4.sqlSELECT 'alter table ' || t_column.table_name || ' modify ' ||t_column.column_name || ' varchar2(' || (t_column.data_length + ceil(t_column.data_length * 0.5)) || ');' AS alter_sqlstrFROM user_tab_columns t_column, user_tables t_tablesWHERE t_column.table_name = t_tables.table_nameAND t_column.data_length <= 2600AND t_column.data_type = 'VARCHAR2'; SQL> spool off
8、执行需要扩容的SQL文本:
[oracle@rac1 ~]# sqlplus baj/123456
###连接到baj用户执行下面操作SQL> /home/oracle/char1.sql
SQL> /home/oracle/char2.sql
SQL> /home/oracle/char3.sql
SQL> /home/oracle/char4.sql
###执行char1.sql、char2.sql、char3.sql、char4.sql之前,需要删除多余的spool和spool off内容只保留alter table内容
9、如果有些表扩长到varchar2(4000)也不足,所以需要修改为clob数据类型
ps:在第一次导入的时候发现导入WA_CLASSITEM表时,VFORMULASTR字段扩容到了varchar2(4000),但数据长度需要4070,varchar2最大长度为4000,所以只能通过alter table修改数据类型为clob才能解决,那么只能将生产用户删掉,然后再来一遍哦!

SQL> ALTER TABLE WA_CLASSITEM DROP COLUMN VFORMULASTR;
SQL> ALTER TABLE WA_CLASSITEM add VFORMULASTR CLOB;
10、linux下使用impdp工具导入(导入对象的数据):
[oracle@rac1 ~]# export ORACLE_SID=baj1
[oracle@rac1 ~]# echo $ORACLE_SID[oracle@rac1 ~]# impdp system/oracle directory=baj_dir dumpfile=expdp_orcl_baj_01.dmp,expdp_orcl_baj_02.dmp,expdp_orcl_baj_03.dmp,expdp_orcl_baj_04.dmp logfile=impdp_baj_baj_data_only.log schemas=baj parallel=8 CONTENT=data_only table_exists_action=append cluster=n
####impdp导入之前,需要在目标数据库上创建相应表空间对象即可;而对于imp导入时需要在目标数据库上创建相应的用户、权限、表空间等对象。
验证数据部分
第一步:验证数据大小
SQL> select sum(bytes) / 1024 / 1024 / 1024 || 'G' sumfrom dba_segmentswhere owner in ('BAJ')
第二步:验证有无失效的对象(目标数据库上执行)
SQL> select * from dba_objects where status!='VALID' and owner in('BAJ');
SQL> @?/rdbms/admin/utlrp.sql ---有无效对象的话,进行无效对象的编译(最大可能自动修复无效对象)。
第三步:收集统计信息(目标数据库上执行)
[oracle@rac1 ~]# vi status.sql begin
dbms_stats.gather_database_stats;
end;
/ [oracle@rac1 ~]# nohup sqlplus / as sysdba @status.sql & ---因为收集统计信息时间长,所以写个sh后台运行
第四步:查看哪些表的统计信息被锁定(stattype_locked字段为ALL的表示锁定了表的统计信息,默认stattype_locked字段为空表示可以收集统计信息):
SQL> select * from dba_ind_statistics where stattype_locked='ALL' AND OWNER='BAJ';
SQL> select * from dba_tab_statistics where stattype_locked='ALL' AND OWNER='BAJ';SQL> begindbms_stats.unlock_schema_stats(ownname => 'BAJ');end;/

第五步:验证对象(目标数据库上执行)
SQL> select object_type t_object_type, count(*) t_countfrom dba_objectswhere owner in('BAJ')group by object_type
###注:oracle的对象类型可以分的很详细,表、表分区、表子分区是不同的类型。

第六步:对比导入和导出日志

第七步:将undo时间修改回最佳值
SQL> alter system set undo_retention=10800 scope=both sid='*';
兄弟们终于写完了!!!这篇文章是我在下班后写了3个小时奋战到深夜23点才搞定的,之所以分享是因为大家之后肯定会用到的,所以别吝啬你的小手, 点赞、收藏、加关注 。给我来点动力呗。那么我们下一篇文章见——expdp/impdp高效完成全部生产用户的全库迁移。
相关文章:
【Oracle篇】跨字符集迁移:基于数据泵的ZHS16GBK转AL32UTF8全流程迁移
💫《博主主页》:奈斯DB-CSDN博客 🔥《擅长领域》:擅长阿里云AnalyticDB for MySQL(分布式数据仓库)、Oracle、MySQL、Linux、prometheus监控;并对SQLserver、NoSQL(MongoDB)有了解 💖如果觉得文章对你有所帮…...
Qt子模块的功能介绍
一、Qt 主要子模块的功能介绍 1. 核心模块 模块名称功能描述QtCore核心非GUI功能(信号槽、线程、文件IO、容器类、JSON/XML处理等)QtGui基础图形绘制(窗口系统集成、OpenGL抽象、图像处理、字体管理等)QtConcurrent高级多线程API(并行计算框架,如QtConcurrent::run)QtN…...
FRP练手:hello,world实现
方案一:使用 Flask(推荐) from flask import Flaskapp Flask(__name__)app.route(/) def hello_world():return "你好啊世界"if __name__ __main__:# 监听所有网络接口(0.0.0.0),端口 3344app.…...
《深入探秘:分布式软总线自发现、自组网技术原理》
在当今数字化浪潮中,分布式系统的发展日新月异,而分布式软总线作为实现设备高效互联的关键技术,其自发现与自组网功能宛如打开智能世界大门的钥匙,为多设备协同工作奠定了坚实基础。 分布式软总线的重要地位 分布式软总线是构建…...
西门子S7-1200PLC 工艺指令PID_Temp进行控温
1.硬件需求: 西门子PLC:CPU 1215C DC/DC/DC PLC模块:SM 1231 TC模块 个人电脑:已安装TIA Portal V17软件 加热套:带加热电源线以及K型热电偶插头 固态继电器:恩爵 RT-SSK4A2032-08S-F 其他࿱…...
提升Windows安全的一些措施
由简单到复杂,仅供参考 一、杀毒软件: 1、杀毒能力: https://haokan.hao123.com/v?vid3883775443252827335&pdhaokan_share 2、使用注意: 一台主机只安装一个杀毒软件就可以了 杀毒软件会误报,造成正常文件…...
Jupyter notebook定制字体
一、生成配置文件 运行Anaconda Powershell Prompt终端,输入下面一行代码: jupyter notebook --generate-config 将生成文件“C:\Users\XXX\.jupyter\jupyter_notebook_config.py”,XXX为计算机账户名字。 二、修改配置文件 c.NotebookAp…...
内存分配中的堆(Memory Heap)详解
在计算机科学中,"堆"这个术语确实容易让人混淆,因为它同时用于描述两种完全不同的概念:数据结构中的堆和内存管理中的堆。上次我们讨论了数据结构中的堆,今天我将详细解释内存分配中的堆(Memory Heap&#x…...
vant4+vue3上传一个pdf文件并实现pdf的预览。使用插件pdf.js
注意下载的插件的版本"pdfjs-dist": "^2.2.228", npm i pdfjs-dist2.2.228 然后封装一个pdf的遮罩。因为pdf文件有多页,所以我用了swiper轮播的形式展示。因为用到移动端,手动滑动页面这样比点下一页下一页的方便多了。 直接贴代码…...
JS | 函数柯里化
函数柯里化(Currying):将一个接收多个参数函数,转换为一系列只接受一个参数的函数的过程。即 逐个接收参数。 例子: 普通函数: function add(a, b, c) {return a b c; } add(1, 2, 3); // 输出 6柯里化…...
软件工程基础之设计模式
目录 单例模式(Singleton Pattern)工厂方法模式(Factory Method Pattern)抽象工厂模式(Abstract Factory Pattern)原型模式(Prototype Pattern)适配器模式(Adapter Pattern)单例模式(Singleton Pattern) 确保一个类只有一个实例,并提供一个全局访问点。应用场景:…...
2025 数字中国创新大赛数字安全赛道数据安全产业积分争夺赛初赛-东部赛区WriteUp
2025 数字中国创新大赛数字安全赛道数据安全产业积分争夺赛初赛-东部赛区WriteUp 数据安全:ez_upload(60分): 模型安全:数据分析:溯源与取证:1-1:1-2: 数据社工:2-2:2-3:2-4: 数据跨境ÿ…...
2025 年网络安全终极指南
我们生活在一个科技已成为日常生活不可分割的一部分的时代。对数字世界的依赖性日益增强的也带来了更大的网络风险。 网络安全并不是IT专家的专属特权,而是所有用户的共同责任。通过简单的行动,我们可以保护我们的数据、隐私和财务,降低成为…...
1.6-抓包技术(Burp Suite\Yakit抓包\Web、APP、小程序)
1.6-抓包技术(Burp Suite\Yakit抓包\Web、APP、小程序) 如果要使用抓包软件,基本上第一步都是要安装证书的。原因如下: 客户端(浏览器或应用)会检测到证书不受信任,并弹出 证书错误࿰…...
图解力扣回溯及剪枝问题的模板应用
文章目录 选哪个的问题17. 电话号码的字母组合题目描述解题代码图解复杂度 选不选的问题78. 子集题目描述解题代码图解复杂度 两相转化77. 组合题目描述解题代码法一:按选哪个的思路法二:按选不选的思路 图解选哪个:选不选 复杂度 选哪个的问…...
Elasticsearch 8.X 如何利用嵌入向量提升搜索能力?
众所周知,Elasticsearch 是一个非常流行的搜索引擎,因为它速度快、扩展性强,尤其擅长全文搜索。 近两年,向量嵌入(Vector Embedding)技术的引入,让 Elasticsearch 在处理高级搜索场景时变得更强…...
MySQL体系架构(一)
1.1.MySQL的分支与变种 MySQL变种有好几个,主要有三个久经考验的主流变种:Percona Server,MariaDB和 Drizzle。它们都有活跃的用户社区和一些商业支持,均由独立的服务供应商支持。同时还有几个优秀的开源关系数据库,值得我们了解一下。 1.1.1.Drizzle Drizzle是真正的M…...
【Docker项目实战】使用Docker部署ToDoList任务管理工具
【Docker项目实战】使用Docker部署ToDoList任务管理工具 一、ToDoList介绍1.1 ToDoList简介1.2 ToDoList主要特点二、本次实践规划2.1 本地环境规划2.2 本次实践介绍三、本地环境检查3.1 检查Docker服务状态3.2 检查Docker版本3.3 检查docker compose 版本四、下载ToDoList镜像…...
深度强化学习基础 0:通用学习方法
过去自己学习深度强化学习的痛点: 只能看到各种术语、数学公式勉强看懂,没有建立清晰且准确关联 多变量交互关系浮于表面,有时候连环境、代理控制的变量都混淆 模型种类繁多,概念繁杂难整合、对比或复用,无框架分析所…...
Traefik应用:配置容器多个网络时无法访问问题
Traefik应用:配置容器多个网络时无法访问问题 介绍解决方法问题原因: **容器多网络归属导致 Traefik 无法正确发现路由规则**。解决方案方法 1:将应用容器 **仅连接** 到 traefik-public 网络方法 2:显式指定 Traefik 监听的网络 …...
虚幻5的C++调试踩坑
本地调试VS附加调试 踩坑1 预编译版本的UE5没有符号文件,无法调试源码 官方代码调试所需要的符号文件bdp需要下载导入。我安装的5.5.4是预编译版本,并非ue5源码。所以不含bdp文件。需要调试官方代码则需要通过EPIC中下载安装。右键UE版本,打…...
react 中将生成二维码保存到相册
需求:生成二维码,能保存到相册 框架用的 react 所以直接 qrcode.react 插件,然后直接用插件生成二维码,这里一定要写 renderAs{‘svg’} 属性,否则会报错,这里为什么会报错??&#…...
通信协议详解(十):PSI5 —— 汽车安全传感器的“抗干扰狙击手”
一、PSI5是什么? 一句话秒懂 PSI5就像传感器界的“防弹信使”:在汽车安全系统(如气囊)中,用两根线同时完成供电数据传输,即便车祸时线路受损,仍能确保关键信号准确送达! 基础概念…...
C语言【模仿strcpy】
题目 模仿strcpy 思路(注意事项) 注意需要在复制的字符串结尾加\0表示字符串的终止 纯代码 #include<stdio.h>void cpy(const char *a, char *b){int i 0;while (a[i] ! \0){b[i] a[i];i ;}b[i] \0; } int main(){char a[] "HELLO&quo…...
从零开始学Python游戏编程18-函数3
《从零开始学Python游戏编程17-函数2》中,通过代码重构的方式将游戏的主要代码写入到自定义函数runGame()中。对于runGame()中的代码,可以继续对其进行重构,以达到简化代码结构的目的。 1 自定义函数askPlayer() 1.1 函数作用 自定义函数a…...
Spring事务传播机制
Spring 事务传播机制定义了在多个事务方法相互调用时,事务如何在这些方法间传播。它决定了一个事务方法调用另一个事务方法时,新的事务是如何开启、是否要加入已有的事务等情况。Spring 提供了 7 种事务传播行为,下面是详细介绍。 解释说明&…...
不同PHP框架之间的兼容性问题及应对策略!
在PHP开发领域,Laravel、Symfony、Yii、ThinkPHP、亿坊PHP等框架因其高效性和便捷性广受开发者青睐。但当项目需要跨框架协作或迁移时,兼容性问题直击要害。本文将从实际案例出发,剖析不同PHP框架间常见的兼容性痛点,并为大家提供…...
Qt 子项目依赖管理:从原理到实践的最佳分析:depends还是 CONFIG += ordered
1. 问题背景 在Qt项目开发中,当一个工程包含多个子项目(如库、插件、测试模块)时,如何正确管理它们的构建顺序和依赖关系? 如: 在开发一个包含核心库(core)、GUI模块(g…...
大数据专业学习路线
大数据专业学习路线 目录 基础知识核心技术进阶技能实战项目职业发展学习资源学习计划常见问题 1. 基础知识 1.1 编程语言 Python:大数据分析的基础语言 基础语法和数据类型函数和模块面向对象编程文件操作和异常处理常用库:NumPy, Pandas, Matplot…...
点云从入门到精通技术详解100篇-基于点云的三维多目标追踪与目标检测
目录 知识储备 基于Python和Open3D库实现的三维点云多目标检测与跟踪 技术要点解析 : 运行环境配置: 扩展改进建议 : 前言 三维多目标追踪技术 点云目标检测算法 2 二维多目标追踪框架及三维点云目标检测 2.1 二维多目标追踪框架 2.1.1 Deep SORT总体架构 2.1…...











