您的位置:首页 > 数据库 > Oracle

oracle中中英文段落划分实现

2016-01-26 15:42 681 查看
oracle中关于中文占用字节数,不同的数据库有不同的情况,有的占用两个字节、有的占用三个字节,现在测试环境的数据库中文占用三个字节,要实现由中英文组成的段落字符串,按照每行占用多少字节重新分段,具体应用是在润乾报表展现。

由于中文字符占用三个字节一个字符,英文字符及数字占用一个字节一个字符,通过字符去判定一行多少字,最后会出现全部汉字的一行跟全部数字的一行无法对其的情况,所以最终考虑用字节去判定一行占用字节数,最后段落划分以及对齐都能满足需求。

具体实例实现:

一、数据库中字段存储的原始值



二、通过函数调用实现需求

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;


三、通过函数转换后查询值



四、转后字段在润乾中展现效果

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: