oracle中中英文段落划分实现
2016-01-26 15:42
681 查看
oracle中关于中文占用字节数,不同的数据库有不同的情况,有的占用两个字节、有的占用三个字节,现在测试环境的数据库中文占用三个字节,要实现由中英文组成的段落字符串,按照每行占用多少字节重新分段,具体应用是在润乾报表展现。
由于中文字符占用三个字节一个字符,英文字符及数字占用一个字节一个字符,通过字符去判定一行多少字,最后会出现全部汉字的一行跟全部数字的一行无法对其的情况,所以最终考虑用字节去判定一行占用字节数,最后段落划分以及对齐都能满足需求。
具体实例实现:
一、数据库中字段存储的原始值
二、通过函数调用实现需求
select FUN_STR_SPLIT(k.COMMENTS) as text_COMMENTS_first from table_name k;
三、通过函数转换后查询值
四、转后字段在润乾中展现效果
由于中文字符占用三个字节一个字符,英文字符及数字占用一个字节一个字符,通过字符去判定一行多少字,最后会出现全部汉字的一行跟全部数字的一行无法对其的情况,所以最终考虑用字节去判定一行占用字节数,最后段落划分以及对齐都能满足需求。
具体实例实现:
一、数据库中字段存储的原始值
二、通过函数调用实现需求
select FUN_STR_SPLIT(k.COMMENTS) as text_COMMENTS_first from table_name k;
CREATE OR REPLACE FUNCTION FUN_STR_SPLIT(pStr IN VARCHAR2) RETURN VARCHAR2 AS V_LENGTH NUMBER;--字符长度 V_STR VARCHAR2(4000); V_STR_T VARCHAR2(4000); V_STR_RET VARCHAR2(4000); V_TEMP VARCHAR2(4000); V_TEMP_CHAR VARCHAR2(20); V_TEMP_CHAR_T VARCHAR2(20); V_TEMP_CHAR_W VARCHAR2(20); V_COUNT NUMBER;--回车<BR>数量 V_COUNT_CH NUMBER;--中文占用字节数 V_COUNT_NUM NUMBER;--是否是汉字判断 V_COUNT_CH_NUM NUMBER;--中文标点 I NUMBER; J NUMBER; BEGIN I :=1; J :=1; V_COUNT :=0; --将字符串中回车 换成 <BR> --SELECT REPLACE(REPLACE(PSTR,CHR(10),'<BR>'),' ','') INTO V_TEMP FROM DUAL; SELECT REPLACE(PSTR,CHR(10),'<BR>') INTO V_TEMP FROM DUAL; --计算字符长度 SELECT LENGTH(V_TEMP) INTO V_LENGTH FROM DUAL; --计算中文占用字节数 SELECT LENGTHB('啊') INTO V_COUNT_CH FROM DUAL; --循环判断字符 WHILE I < V_LENGTH+1 LOOP --获取对应位置字符 V_TEMP_CHAR:=SUBSTR(V_TEMP,I,1); --判断是否是中文 select instr('1234567890ABCDEFGHIJKLMNOPQRSTUVWXYZ!@#$%^&*();:/?,<>',upper(V_TEMP_CHAR)) into V_COUNT_CH from dual; if j < 72 then --如果是中文 (中文占用三个字节) if V_COUNT_CH > 0 then --判断当前字符的下一个是不是<BR> V_TEMP_CHAR_T:=SUBSTR(V_TEMP,I+1,1); if V_TEMP_CHAR_T = '<' then V_TEMP_CHAR:=SUBSTR(V_TEMP,I,5); V_STR :=V_STR||V_TEMP_CHAR; J :=1; I :=I+5; V_COUNT :=V_COUNT+1; else V_STR :=V_STR||V_TEMP_CHAR; i :=i+1; j :=j+1; end if; else --判断当前字符的下一个是不是<BR> V_TEMP_CHAR_T:=SUBSTR(V_TEMP,I+1,1); if V_TEMP_CHAR_T = '<' then V_TEMP_CHAR:=SUBSTR(V_TEMP,I,5); V_STR :=V_STR||V_TEMP_CHAR; J :=1; I :=I+5; V_COUNT :=V_COUNT+1; else V_STR :=V_STR||V_TEMP_CHAR; i :=i+1; j :=j+3; end if; end if; else --判断当前字符的下一个是不是<BR> V_TEMP_CHAR_T:=SUBSTR(V_TEMP,I+1,1); --判断当前字符的下下一个是不是<BR> V_TEMP_CHAR_W:=SUBSTR(V_TEMP,I+2,1); if V_TEMP_CHAR_T = '<' then V_TEMP_CHAR:=SUBSTR(V_TEMP,I,5); V_STR :=V_STR||V_TEMP_CHAR; J :=1; I :=I+5; V_COUNT :=V_COUNT+1; elsif V_TEMP_CHAR_T = chr(13) then if V_TEMP_CHAR_W = '<' then V_TEMP_CHAR:=SUBSTR(V_TEMP,I,5); V_STR :=V_STR||V_TEMP_CHAR; J :=1; I :=I+5; V_COUNT :=V_COUNT+1; end if; else --判断中文标点 select instr('。,?!.',upper(V_TEMP_CHAR_T)) into V_COUNT_CH_NUM from dual; if V_COUNT_CH_NUM > 0 then V_STR :=V_STR||V_TEMP_CHAR||V_TEMP_CHAR_T||'<BR>'; J:=1; I :=I+2; V_COUNT :=V_COUNT+1; else V_STR :=V_STR||V_TEMP_CHAR||'<BR>'; J:=1; I :=I+1; V_COUNT :=V_COUNT+1; end if; end if; end if; END LOOP; RETURN(V_STR); END FUN_STR_SPLIT;
三、通过函数转换后查询值
四、转后字段在润乾中展现效果
相关文章推荐
- 给oracle写自增序列
- Oracle之UTL_FILE 包用法详解
- 在 Oracle Enterprise Linux 和 iSCSI 上构建您自己的 Oracle RAC 集群 (3)
- 在 Oracle Enterprise Linux 和 iSCSI 上构建您自己的 Oracle RAC 11g 集群 (2)
- oracle改变ip后的问题
- 在 Oracle Enterprise Linux 和 iSCSI 上构建您自己的 Oracle RAC 11g 集群 (1)
- 如何使用sysdba身份通过jdbc连接oracle?
- oracle或mysql分组查询并且获取前3条排序后的数据
- oracle将普通表变分区表
- Oracle Enterprise Manager Cloud Control 12c R4 安装配置
- oracle表空间不足扩容的方法
- ORACLE查询技巧----OVER(PARTITION BY)
- 基于Oracle数据库操作的SQL基础语法
- oracle的physical dataguard的配置过程
- oracle远程导入导出数据库
- oracle 新建用户、表空间
- Oracle存储过程中常见异常记录
- Oracle 表操作
- Oracle 删除重复数据只留一条
- oracle数据库表分区基本语句