今天有朋友數據庫出現ORA-29275 部分多字節字符,對應的字段只能用to_char才能正常查詢,感覺是字符集問題。詢問之果然修改過字符集。
他的修改方式:
SQL>STARTUP MOUNT; SQL>ALTER SYSTEM ENABLE RESTRICTED SESSION; SQL>ALTER SYSTEM SET JOB_QUEUE_PROCESSES=0; SQL>ALTER SYSTEM SET AQ_TM_PROCESSES=0; SQL>ALTER DATABASE OPEN; SQL>ALTER DATABASE CHARACTER SET INTERNAL_USE ZHS16GBK;
SQL> select name,value$ from props$ where name like '%NLS%'; NAME VALUE$ ------------------------------ ------------------------------ NLS_LANGUAGE AMERICAN NLS_TERRITORY AMERICA NLS_CURRENCY $ NLS_ISO_CURRENCY AMERICA NLS_NUMERIC_CHARACTERS ., NLS_CHARACTERSET ZHS16GBK NLS_CALENDAR GREGORIAN NLS_DATE_FORMAT DD-MON-RR NLS_DATE_LANGUAGE AMERICAN NLS_SORT BINARY NLS_TIME_FORMAT HH.MI.SSXFF AM NLS_TIMESTAMP_FORMAT DD-MON-RR HH.MI.SSXFF AM NLS_TIME_TZ_FORMAT HH.MI.SSXFF AM TZR NLS_TIMESTAMP_TZ_FORMAT DD-MON-RR HH.MI.SSXFF AM TZR NLS_DUAL_CURRENCY $ NLS_COMP BINARY NLS_LENGTH_SEMANTICS BYTE NLS_NCHAR_CONV_EXCP FALSE NLS_NCHAR_CHARACTERSET AL16UTF16 NLS_RDBMS_VERSION 11.2.0.1.0確實已經修改好了。但是這裡:
ALTER DATABASE CHARACTER SET INTERNAL_USE ZHS16GBK;是非常有問題的,這裡跳過字符集子集檢查,強制進行修改。
所以以後的數據將會出現問題。
那麼我們使用exp/imp在導出的時候指定字符集進行轉換呢?
引入一篇文章的部分段落:
9i之前的版本:在源數據庫的字符集和export的session的NLS_LANG設置不同時,所有數據的字符集(用戶數據和字典數據)均會轉換;
在import過程中,如果import session的NLS_LANG和export時不一致,將會將dmp中的字符集轉換成import session的NLS_LANG設置成的字符集;
當import session的NLS_LANG和目標數據庫的字符集不一致時,將會發生公import session的NLS_LANG字符集到目標數據庫的字符集轉換
9i及之後的版本:在源數據庫的字符集和export的session的NLS_LANG設置不同時,只有字典數據會發生字符集轉換,用戶數據則和源數據庫的字符集一致,而忽略NLS_LANG的設置;
在import過程中,如果import session的NLS_LANG和export時不一致,將會將dmp中的字符集轉換成import session的NLS_LANG設置成的字符集;
當import session的NLS_LANG和目標數據庫的字符集不一致時,將會發生公import session的NLS_LANG字符集到目標數據庫的字符集轉換
其實都沒關系,不管你用什麼辦法轉換,只要轉換的字符集不是原字符集的超集都是有問題的:
所以我們在修改數據庫字符集的時候,執行如下語句:
ALTER DATABASE CHARACTER SET ZHS16GBK
如果沒有報:
SYS@zbdba>ALTER DATABASE CHARACTER SET ZHS16GBK; ALTER DATABASE CHARACTER SET ZHS16GBK * ERROR at line 1: ORA-12712: new character set must be a superset of old character set那說明可以修改。如果有以上錯誤,建議不要修改強制修改字符集