20.2. 字元集支援

PostgreSQL 裡面的字元集支援您能夠以各種字元集儲存文本, 包括單字元的字元集,比如 ISO 8859 系列和 EUC (擴展 Unix 編碼 Extended Unix Code),Unicode 和 Mule 國際編碼。所有字元集都可以在伺服器上透明地使用。 (如果您使用了來自其它資料源地擴展函數,那麼它取決於他們是否正確地書寫了代碼。) 預設的字元集是在使用 initdb 初始化您的 PostgreSQL 資料庫集群的時候選擇的。 在您的使用 createdb 或者 SQL 命令 CREATE DATABASE 的時候是可以覆蓋這個預設的。因此,您可以有多個資料庫,每個都有不同的字元集。

20.2.1. 支援字元集編碼

Table 20-1 顯示了可以用在伺服器的字元集。

Table 20-1. 伺服器字元集

名字描述
SQL_ASCIIASCII
EUC_JP日文 EUC
EUC_CN中文 EUC
EUC_KR韓文 EUC
JOHAB韓文 EUC (Hangle base)
EUC_TW台灣 EUC
UNICODEUnicode(UTF-8)
MULE_INTERNALMule 內部編碼
LATIN1ISO 8859-1/ECMA 94 (Latin Alphabet No.1)
LATIN2ISO 8859-2/ECMA 94 (Latin Alphabet No.2)
LATIN3ISO 8859-3/ECMA 94 (Latin Alphabet No.3)
LATIN4ISO 8859-4/ECMA 94 (Latin Alphabet No.4)
LATIN5ISO 8859-9/ECMA 128 (Latin Alphabet No.5)
LATIN6ISO 8859-10/ECMA 144 (Latin Alphabet No.6)
LATIN7ISO 8859-13 (Latin Alphabet no.7)
LATIN8ISO 8859-14 (Latin Alphabet no.8)
LATIN9ISO 8859-15 (Latin Alphabet no.9)
LATIN10ISO 8859-16/ASRO SR 14111 (Latin Alphabet no.10)
ISO_8859_5ISO 8859-5/ECMA 113 (Latin/Cyrillic)
ISO_8859_6ISO 8859-6/ECMA 114 (Latin/Arabic)
ISO_8859_7ISO 8859-7/ECMA 118 (Latin/Greek)
ISO_8859_8ISO 8859-8/ECMA 121 (Latin/Hebrew)
KOI8KOI8-R(U)
ALTWindows CP866
WIN874Windows CP874 (Thai)
WIN1250Windows CP1250
WINWindows CP1251
WIN1256Windows CP1256 (Arabic)
TCVNTCVN-5712/Windows CP1258 (Vietnamese)

Important: PostgreSQL7.2 之前, LATIN5錯誤地資料表示 ISO 8859-5 的意思。 從 7.2 開始 LATIN5資料表示 ISO8859-9。 如果您有一個在 7.1 或者之前建立的使用了 LATIN5的資料庫, 而且您希望移植到 7.2(或者以後的版本), 那麼您必須非常仔細地注意這個變化。

並非所有API支援上面列出的編碼。比如, PostgreSQL JDBC 驅動就不支援MULE_INTERNALLATIN6LATIN8LATIN10

20.2.2. 設置字元集

initdb 為一個 PostgreSQL 集群定義預設的字元集,比如:

initdb -E EUC_JP

把預設字元集設置為 EUC_JP (用於日文的擴展的 Unix 編碼)。 如果您喜歡用長選項聲明的話,您可以用 --encoding 代替 -E。 如果沒有給出-E或者--encoding選項, 則使用SQL_ASCII

您可以建立一個有著不同編碼的資料庫:

createdb -E EUC_KR korean

將建立一個使用EUC_KR字元集的名字叫 korean 的資料庫。 另外一種實現方法是使用 SQL 命令:

CREATE DATABASE korean WITH ENCODING 'EUC_KR';

資料庫的編碼是用系統資料表 pg_database 裡的一個 編碼字串代資料表的。 您可以用psql-l選項或 \l命令列出這些編碼。

$ psql -l
            List of databases
   Database    |  Owner  |   Encoding
---------------+---------+---------------
 euc_cn        | t-ishii | EUC_CN
 euc_jp        | t-ishii | EUC_JP
 euc_kr        | t-ishii | EUC_KR
 euc_tw        | t-ishii | EUC_TW
 mule_internal | t-ishii | MULE_INTERNAL
 regression    | t-ishii | SQL_ASCII
 template1     | t-ishii | EUC_JP
 test          | t-ishii | EUC_JP
 unicode       | t-ishii | UNICODE
(9 rows)

Important: 雖然您可以給一個資料庫聲明您需要的任何編碼,但選擇一個與您選擇的區域不一致的編碼還是不妥的做法。 LC_COLLATELC_CTYPE 設置暗示一個特定的編碼, 與區域相關的操作(比如排序)在不兼容的編碼裡很有可能產生錯誤的解析。

因為這些區域設置都是由 initdb 凍結的, 所以在不同的資料庫裡使用不同的編碼更多是理論而不是現實。 這些機制很有可能在將來版本的 PostgreSQL 得到改進。

一個安全使用多種編碼的方法是在 initdb 的時候把區域設置為 C 或者 POSIX,這樣舊關閉了任何實際的區域敏感性。

20.2.3. 伺服器和客戶端之間的自動字元集轉換

PostgreSQL 支援一些編碼在伺服器和前端之間的自動編碼轉換。 轉換訊息在系統資料表 pg_conversion 中儲存。 您可以使用 SQL 命令 CREATE CONVERSION 建立一個新的轉換。 PostgreSQL帶著一些預定義的轉換。它們在 Table 20-2 中列出。

Table 20-2. 客戶/伺服器字元集轉換

伺服器字元集可用客戶端字元集
SQL_ASCIISQL_ASCII, UNICODE, MULE_INTERNAL
EUC_JPEUC_JP, SJIS, UNICODE, MULE_INTERNAL
EUC_CNEUC_CN, UNICODE, MULE_INTERNAL
EUC_KREUC_KR, UNICODE, MULE_INTERNAL
JOHABJOHAB, UNICODE
EUC_TWEUC_TW, BIG5, UNICODE, MULE_INTERNAL
LATIN1LATIN1, UNICODE, MULE_INTERNAL
LATIN2LATIN2, WIN1250, UNICODE, MULE_INTERNAL
LATIN3LATIN3, UNICODE, MULE_INTERNAL
LATIN4LATIN4, UNICODE, MULE_INTERNAL
LATIN5LATIN5, UNICODE
LATIN6LATIN6, UNICODE, MULE_INTERNAL
LATIN7LATIN7, UNICODE, MULE_INTERNAL
LATIN8LATIN8, UNICODE, MULE_INTERNAL
LATIN9LATIN9, UNICODE, MULE_INTERNAL
LATIN10LATIN10, UNICODE, MULE_INTERNAL
ISO_8859_5ISO_8859_5, UNICODE, MULE_INTERNAL, WIN, ALT, KOI8
ISO_8859_6ISO_8859_6, UNICODE
ISO_8859_7ISO_8859_7, UNICODE
ISO_8859_8ISO_8859_8, UNICODE
UNICODE EUC_JP, SJIS, EUC_KR, UHC, JOHAB, EUC_CN, GBK, EUC_TW, BIG5, LATIN1LATIN10, ISO_8859_5, ISO_8859_6, ISO_8859_7, ISO_8859_8, WIN, ALT, KOI8, WIN1256, TCVN, WIN874, GB18030, WIN1250
MULE_INTERNALEUC_JP, SJIS, EUC_KR, EUC_CN, EUC_TW, BIG5, LATIN1LATIN5, WIN, ALT, WIN1250 BIG5, ISO_8859_5, KOI8
KOI8ISO_8859_5, WIN, ALT, KOI8, UNICODE, MULE_INTERNAL
ALTISO_8859_5, WIN, ALT, KOI8, UNICODE, MULE_INTERNAL
WINISO_8859_5, WIN, ALT, KOI8, UNICODE, MULE_INTERNAL
WIN874WIN874, UNICODE
WIN1250LATIN2, WIN1250, UNICODE, MULE_INTERNAL
WINISO_8859_5, WIN, ALT, KOI8, UNICODE, MULE_INTERNAL
WIN1256WIN1256, UNICODE
TCVNTCVN, UNICODE

要想打開自動字元集轉換功能,您必須告訴 PostgreSQL 您想在客戶端使用的字元集(編碼)。您可以用好幾種方法實現這個目的。

假如無法進行特定的字元轉換 — 比如, 您選的伺服器編碼是EUC_JP, 客戶端是LATIN1,那麼有些日文字元不能轉換成LATIN1。這時, 不能用LATIN1字元集資料表示的字母將被轉換成圓括弧包圍的十六進制,像,(826C) 這樣。

20.2.4. 進一步閱讀

下面是學習各種類型的編碼系統的好地方。

ftp://ftp.ora.com/pub/examples/nutshell/ujip/doc/cjk.inf

詳細地解釋了第3.2節出現的EUC_JPEUC_CNEUC_KREUC_TW

http://www.unicode.org/

Unicode 的家目錄。

RFC 2044

定義了UTF-8。