Plsql 来自utf8的oracle utl_文件编码
我喜欢将大量文本数据从数据库导出到文件。 db中的字符集是UTF8。 文件中的例外结果是ISO8859P2或MSWIN1250 我的数据库设置:Plsql 来自utf8的oracle utl_文件编码,plsql,utf-8,character-encoding,ansi,utl-file,Plsql,Utf 8,Character Encoding,Ansi,Utl File,我喜欢将大量文本数据从数据库导出到文件。 db中的字符集是UTF8。 文件中的例外结果是ISO8859P2或MSWIN1250 我的数据库设置: SELECT * FROM v$nls_parameters; 1 NLS_LANGUAGE HUNGARIAN 0 2 NLS_TERRITORY HUNGARY 0 9 NLS_CHARACTERSET UTF8 0 10 NLS_SORT HUNGARIAN 0 16 NLS_NCHAR_CHA
SELECT * FROM v$nls_parameters;
1 NLS_LANGUAGE HUNGARIAN 0
2 NLS_TERRITORY HUNGARY 0
9 NLS_CHARACTERSET UTF8 0
10 NLS_SORT HUNGARIAN 0
16 NLS_NCHAR_CHARACTERSET UTF8 0
17 NLS_COMP BINARY 0
18 NLS_LENGTH_SEMANTICS CHAR 0
19 NLS_NCHAR_CONV_EXCP FALSE 0
select * from nls_database_parameters;
1 NLS_RDBMS_VERSION 12.1.0.2.0
2 NLS_NCHAR_CONV_EXCP FALSE
15 NLS_NCHAR_CHARACTERSET UTF8
16 NLS_CHARACTERSET UTF8
19 NLS_TERRITORY AMERICA
20 NLS_LANGUAGE AMERICAN
select * from nls_session_parameters;
1 NLS_LANGUAGE HUNGARIAN
2 NLS_TERRITORY HUNGARY
9 NLS_SORT HUNGARIAN
15 NLS_COMP BINARY
16 NLS_LENGTH_SEMANTICS CHAR
17 NLS_NCHAR_CONV_EXCP FALSE
在服务器目录(linux)中创建的文件。我没有关于linux字符集设置的更多信息
PLSQL代码:
DECLARE
v_fh UTL_FILE.FILE_TYPE;
v_eol VARCHAR2(2);
v_eollen PLS_INTEGER;
CURSOR cur_sql IS
SELECT T3.ID_RESULT
,T3.column1
FROM table1
WHERE id_result = 999999
;
"ID_RESULT" DBMS_SQL.NUMBER_TABLE;
"column1" DBMS_SQL.VARCHAR2A;
BEGIN
EXECUTE IMMEDIATE 'ALTER SESSION SET NLS_DATE_FORMAT = ''YYYY.MM.DD HH24:MI:SS''';
v_eol := CHR(13)||CHR(10);
v_eollen := LENGTH(v_eol);
v_fh := UTL_FILE.FOPEN('REP_DIR','result_test.csv','W', 32000);
OPEN cur_sql;
LOOP
FETCH cur_sql
BULK COLLECT INTO "ID_RESULT",
"column1",
LIMIT 1000;
IF "ID_RESULT".COUNT > 0 THEN
FOR i IN "ID_RESULT".FIRST .. "ID_RESULT".LAST LOOP
UTL_FILE.PUT(v_fh, CONVERT("column1"(i),'EE8ISO8859P2','UTF8'));
UTL_FILE.PUT_nchar(v_fh, v_eol);
UTL_FILE.PUT(v_fh, CONVERT("column1"(i),'EE8MSWIN1250','UTF8'));
UTL_FILE.PUT(v_fh, v_eol);
UTL_FILE.PUT(v_fh, CONVERT("column1"(i),'EE8ISO8859P2'));
UTL_FILE.PUT(v_fh, v_eol);
UTL_FILE.PUT(v_fh, CONVERT("column1"(i),'EE8MSWIN1250'));
UTL_FILE.PUT(v_fh, v_eol);
UTL_FILE.PUT(v_fh, "column1"(i));
UTL_FILE.PUT(v_fh, v_eol);
UTL_FILE.PUT(v_fh, utl_raw.cast_to_varchar2(utl_raw.convert(utl_raw.cast_to_raw("column1"(i) ),'HUNGARIAN_HUNGARY.EE8MSWIN1250', 'ENGLISH_UNITED KINGDOM.UTF8')));
UTL_FILE.PUT(v_fh, v_eol);
UTL_FILE.fflush(v_fh);
END LOOP;
END IF;
EXIT WHEN cur_sql%NOTFOUND;
END LOOP;
CLOSE cur_sql;
UTL_FILE.FCLOSE(v_fh);
EXCEPTION
WHEN
.........
RAISE;
END;
以db为单位的原始值:
结果以Notepad++(UTF8编码):
拉乔森酒店
拉乔森酒店
拉乔森酒店
拉乔森酒店
拉乔森酒店
拉乔森酒店
结果以Notepad++(ANSI编码,字符集:windows-1250)显示:
拉乔森酒店
拉乔森酒店
拉乔森酒店
拉乔森酒店
Csere LajosnĂ)
拉乔森酒店
结果以Notepad++(ANSI编码,字符集:iso-8859-2):
拉乔森酒店
拉乔森酒店
拉乔森酒店
拉乔森酒店
卡塞尔·拉乔森
拉乔森酒店
使用CONVERT时,我丢失了“é”字符。
如何将字符串从UTF8转换为ANSI
谢谢,
佐尔坦这是我的工具箱包-试试看/调整一下。用于不同的代码页输入输出
function dump_dsv_fast(p_query in varchar2
,p_filename in varchar2
,p_dir in varchar2 default c_DEFAULT_DIRECTORY
,p_separator in varchar2 default ';'
,p_text_qualifier in varchar2 default ''
,p_header in boolean default true
,p_eol_format in varchar2 default chr(13) || chr(10)
,p_characterset in varchar2 default 'EE8MSWIN1250'
,p_write_mode in varchar2 default 'WB') return number
/****************************************************
Formats:
AL32UTF8 --> full utf
WE8MSWIN1252 --> no pl chars
WE8MSWIN1250 --> pl ansi
Limitations: this one is faster filing buffer once
* 2014/05/13 --> change to raw (end line character)
* 2016/02/12 --> text qualifier
--> header on/off
--> line length adjust
--> text q
* 2016/03/09 --> codepage
*****************************************************/
is
l_output utl_file.file_type;
l_theCursor integer default dbms_sql.open_cursor;
l_columnValue varchar2(32760);
l_status integer;
l_separator varchar2(10);
l_colCnt number default 0;
l_descTbl dbms_sql.desc_tab;
l_cnt number default 0;
l_buffer raw(32767) := null;
begin
l_output := utl_file.fopen(p_dir, p_filename, p_write_mode, 32760);
dbms_sql.parse(l_theCursor, p_query, dbms_sql.native);
if p_header
then
dbms_sql.describe_columns(l_theCursor, l_colCnt, l_descTbl);
l_separator := '';
for i in 1 .. l_colCnt
loop
if p_characterset = 'EE8MSWIN1250'
then
utl_file.put_raw(l_output,
utl_raw.cast_to_raw(l_separator ||
p_text_qualifier || l_descTbl(i)
.col_name || p_text_qualifier));
else
utl_file.put_raw(l_output,
utl_i18n.string_to_raw(l_separator ||
p_text_qualifier || l_descTbl(i)
.col_name ||
p_text_qualifier,
p_characterset));
end if;
dbms_sql.define_column(l_theCursor, i, l_columnValue, 32760);
l_separator := p_separator;
end loop;
utl_file.put_raw(l_output, utl_raw.cast_to_raw(p_eol_format));
end if;
for i in 1 .. 255
loop
begin
dbms_sql.define_column(l_theCursor, i, l_columnValue, 32760);
l_colCnt := i;
exception
when others then
if (sqlcode = -1007)
then
exit;
else
raise;
end if;
end;
end loop;
dbms_sql.define_column(l_theCursor, 1, l_columnValue, 32760);
l_status := dbms_sql.execute(l_theCursor);
loop
exit when(dbms_sql.fetch_rows(l_theCursor) <= 0);
l_separator := '';
for i in 1 .. l_colCnt
loop
dbms_sql.column_value(l_theCursor, i, l_columnValue);
if p_characterset = 'EE8MSWIN1250'
then
l_buffer := l_buffer ||
utl_raw.cast_to_raw(l_separator || p_text_qualifier ||
l_columnValue || p_text_qualifier);
else
l_buffer := l_buffer ||
utl_i18n.string_to_raw(l_separator || p_text_qualifier ||
l_columnValue ||
p_text_qualifier, p_characterset);
end if;
l_separator := p_separator;
end loop;
utl_file.put_raw(l_output,
l_buffer || utl_raw.cast_to_raw(p_eol_format));
l_buffer := '';
l_cnt := l_cnt + 1;
end loop;
dbms_sql.close_cursor(l_theCursor);
utl_file.fclose(l_output);
return l_cnt;
end dump_dsv_fast;
函数dump\u dsv\u fast(varchar2中的p\u查询
,p_文件名为varchar2
,p_dir在varchar2默认c_默认目录中
,varchar2中的p_分隔符默认为“;”
,varchar2默认值“”中的p_text_限定符
,p_标题为布尔值默认值true
,p|u eol|u格式,在varchar2默认chr(13)| chr(10)
,varchar2中的p_字符集默认值为“EE8MSWIN1250”
,p_write_模式为varchar2默认“WB”)返回编号
/****************************************************
格式:
AL32UTF8-->全utf
WE8MSWIN1252-->无pl字符
WE8MSWIN1250-->pl ansi
限制:这是一个更快的归档缓冲区一次
*2014/05/13-->更改为原始(结束行字符)
*2016/02/12-->文本限定符
-->收割台开/关
-->线路长度调整
-->文本q
*2016/03/09-->代码页
*****************************************************/
是
l_输出utl_文件。文件类型;
l_游标整数默认dbms_sql.open_游标;
l_columnValue varchar2(32760);
l_状态整数;
l_分离器varchar2(10);
l_列数默认为0;
l_descTbl dbms_sql.desc_选项卡;
l_cnt编号默认为0;
l_缓冲区原始值(32767):=null;
开始
l_输出:=utl_file.fopen(p_dir,p_文件名,p_write_模式,32760);
parse(l_theCursor,p_query,dbms_sql.native);
如果p_标题
然后
dbms_sql.描述_列(l_theCursor、l_colCnt、l_descTbl);
l_分隔符:='';
因为我在1。。l_colCnt
环
如果p_characterset='EE8MSWIN1250'
然后
utl_文件。原始放置(l_输出,
utl_原材料。铸造至原材料(l_分离器||
p|u text|u限定符| l|u descTbl(i)
.col|u name | | p|u text_限定符);
其他的
utl_文件。原始放置(l_输出,
utl_i18n.字符串_到_原始(l_分隔符||
p|u text|u限定符| l|u descTbl(i)
上校姓名||
p_text_限定符,
p_字符集);
如果结束;
dbms_sql.define_column(l_theCursor,i,l_columnValue,32760);
l_分离器:=p_分离器;
端环;
utl_文件.put_raw(l_输出,utl_raw.cast_到_raw(p_eol_格式));
如果结束;
因为我在1。。255
环
开始
dbms_sql.define_column(l_theCursor,i,l_columnValue,32760);
l_colCnt:=i;
例外
当其他人
if(sqlcode=-1007)
然后
出口
其他的
提高;
如果结束;
结束;
端环;
dbms_sql.define_column(l_theCursor,1,l_columnValue,32760);
l_status:=dbms_sql.execute(l_构造函数);
环
当(dbms_sql.fetch_行(l_构造函数)时退出