日文及繁體中文延伸 UNIX 程式碼 (EUC) 考量

日文和繁體中文的延伸 UNIX 程式碼 (EUC) 定義一組可支援 1 到 4 個字集的編碼規則。 在某些情況下,例如日文 EUC (eucJP) 和繁體中文 EUC (eucTW) ,字元可以使用兩個以上位元組來編碼。 當使用這類編碼方法作為資料庫伺服器或資料庫用戶端的字碼頁時,會有一些含意。 主要考量包括下列各項:
  • 在 EUC 字碼頁與雙位元組字碼頁之間轉換時字串的擴充或縮減
  • 使用通用字元 Set-2 (UCS-2) 作為以 eucJP (日文) 或 eucTW (傳統中文) 字碼頁定義之資料庫伺服器中儲存的圖形資料的字碼頁。
除了這些考量之外,使用 EUC 與雙位元組字集 (DBCS) 支援一致。 雙位元組 的參照已變更為 多位元組 ,以反映容許字元表示法需要超過 2 個位元組的編碼規則支援。 這裡包括支援日文及繁體中文 EUC 的詳細考量。 任何搭配使用 SQL 與 EUC 資料庫伺服器或 EUC 資料庫用戶端,以及與應用程式開發資訊一起使用的使用者,都應該考量此資訊。

字元

每一個多位元組字元都被視為 字母 ,但雙位元組空白字元除外,它被視為 特殊字元

記號

多位元組小寫英文字母不會轉換成大寫。 這與記號中的單位元組小寫英文字母不同,後者通常會轉換成大寫。

SQL ID

雙位元組字碼頁與 EUC 字碼頁之間的轉換可能會導致將雙位元組字元轉換為以超過 2 個位元組編碼的多位元組字元。 因此,符合雙位元組字碼頁中長度上限的 ID 可能會超出 EUC 字碼頁中的長度。 必須小心選取此類型環境的 ID ,以避免擴充超過 ID 長度上限。

字串

在 MBCS 資料庫中,字串可能包含單位元組字集 (SBCS) 及多位元組字集 (MBCS) 的混合字元。 使用此類字串時,如果作業是以字元為基礎 (將資料視為字元) 或以位元組為基礎 (將資料視為位元組) ,則作業可能會提供不同的結果。 請檢查函數或作業說明,以判定如何處理混合字串。

圖形字串

圖形字串定義為一連串雙位元組字元資料。 為了容許日文或繁體中文 EUC 資料儲存在圖形直欄中, EUC 字元會編碼在 UCS-2中。 在所有受支援的編碼方法 (例如, PC 或 EBCDIC DBCS) 下不是雙位元組字元的字元不應與圖形直欄一起使用。 使用非雙位元組字元的結果可能會導致在轉換期間以替代字元取代。 擷取這類資料將不會傳回與所輸入相同的值。

字串指派

在指派之前執行字串轉換。 在涉及 eucJP/eucTW 字碼頁及 DBCS 字碼頁的情況下,字串可能會變得更長 (DBCS 至 eucJP/eucTW) 或更短 (eucJP/eucTW 至 DBCS)。 這可能會導致儲存體指派發生錯誤,並在擷取指派時截斷。 當在轉換期間由於擴充而導致儲存體指派錯誤時,會傳回 SQLSTATE 22524 而非 SQLSTATE 22001。

同樣地,對於沒有對應的雙位元組字元的字元,涉及圖形字串的指派可能會導致將 UCS-2 編碼的雙位元組字元轉換為 PC 或 EBCDIC DBCS 字碼頁中的替代字元。 以替代字元取代字元的指派會透過將 SQLCA 的 SQLWARN10 欄位設為 'W' 來指出此情況。

在擷取指派期間涉及多位元組字串的截斷情況下,截斷點可能是多位元組字元的一部分。 在此情況下,字元片段的每一個位元組都會取代為單位元組空白。 這表示在截斷的字串結尾可能會出現多個單位元組空白。

字串比較

以位元組為基礎執行字串比較。 字串也會使用為資料庫定義的對照順序。 圖形字串不使用對照順序,並且在 eucJP 或 eucTW 資料庫中使用 UCS-2進行編碼。 因此,兩個混合字串的比較結果可能與兩個圖形字串的比較結果不同,即使它們包含相同的字元。 同樣地,混合字元直欄和圖形直欄的結果排序可能不同。

結果資料類型的規則

字串的可能擴充不會影響字串的結果資料類型。 例如,兩個 CHAR 運算元的聯集仍會是 CHAR。 不過,如果將轉換其中一個字串運算元,使最大擴充使長度屬性成為兩個運算元中的最大,則會影響產生的字串長度屬性。 例如,考量具有 VARCHAR (100) 及 VARCHAR (120) 資料類型之 CASE 表示式的結果表示式。 假設 VARCHAR (100) 表示式是混合字串主變數 (可能需要轉換) ,而 VARCHAR (120) 表示式是 eucJP 資料庫中的直欄。 產生的資料類型是 VARCHAR (200) ,因為 VARCHAR (100) 會加倍以容許可能的轉換。 不涉及 eucJP 或 eucTW 資料庫的相同實務範例將具有結果類型 VARCHAR (120)。

請注意,主變數長度加倍是根據資料庫伺服器是日文 EUC 或繁體中文 EUC 的事實。 即使用戶端也是 eucJP 或 eucTW ,仍會套用加倍。 這可讓雙位元組或多位元組用戶端使用相同的應用程式套件。

字串轉換的規則

SQL Reference 的對應區段中列出的作業類型可能將運算元轉換成應用程式或資料庫字碼頁。

如果在包含日文或繁體中文 EUC 的混合字碼頁環境中執行此類作業,則可能會發生混合字串運算元的擴充或縮減。 因此,如果可能的話,產生的資料類型具有可容納最大擴充的長度屬性。 如果資料類型的長度屬性有限制,則會使用資料類型容許的長度上限。 例如,在最大成長為兩倍的環境中, VARCHAR (200) 主變數會被視為 VARCHAR (400) ,但 CHAR (200) 主變數會被視為 CHAR (255)。 如果已轉換的字串會超出資料類型的長度上限,則在執行轉換時可能會發生執行時期錯誤。 例如, CHAR (200) 和 CHAR (10) 的聯集會有 CHAR (255) 的結果類型。 轉換 UNION 左側的值時,如果需要超過 254 個位元組,則會傳回錯誤。

在某些情況下,容許轉換的最大成長會導致長度屬性超出限制。 例如, UNION 只容許最多 254 個位元組的直欄。 因此,如果查詢的聯集在直欄清單 (稱為 :hv1) 中包含主變數,且是定義為可變長度字串 128 個位元組的 DBCS 混合字串,則會將資料類型設為 VARCHAR (256) ,導致準備查詢時發生錯誤,即使應用程式中的查詢似乎沒有任何直欄大於 254。 在實際字串不可能導致擴充超過 254 個位元組的情況下,可以使用下列指令來準備陳述式。
   SELECT CAST(:hv1 CONCAT ' AS VARCHAR(255)), C2 FROM T1
   UNION
   SELECT C1, C2 FROM T2
空字串與主變數的連結會強制在強制轉型完成之前進行轉換。 雖然在執行時期可能會發生截斷錯誤,但可以在 DBCS 至 eucJP/eucTW 環境中準備此查詢。

此技術 (具有強制轉型的空字串 concat) 可用來處理 SELECT DISTINCT 的類似 254 位元組限制,或使用 ORDER BY 或 GROUP BY 子句中的直欄。

圖形字串常數

日文或繁體中文 EUC 用戶端可以包含單位元組或多位元組字元 (例如混合字串)。 字串不應包含超過 2000 個位元組。 建議只在所有相關 PC 及 EBCDIC 雙位元組字碼頁中使用轉換為雙位元組字元的字元。 SQL 陳述式中的圖形字串常數會在資料庫伺服器上從用戶端字碼頁轉換成雙位元組編碼。 若為日文或繁體中文 EUC 伺服器,常數會轉換為 UCS-2,這是用於圖形字串的雙位元組編碼。 若為雙位元組伺服器,常數會從用戶端字碼頁轉換成伺服器的 DBCS 字碼頁。

函數

使用者定義函數的設計應該考量支援日文或 Tradition-中文 EUC 對參數資料類型的影響。 函數解析的一個部分會考量函數呼叫之引數的資料類型。 包含日文或繁體中文 EUC 用戶端的混合字串引數可能需要額外的位元組來指定引數。 這可能需要變更資料類型以容許增加長度。 例如,可能需要 4001 個位元組才能代表應用程式中適合伺服器上 VARCHAR (4000) 字串的字串 (LONG VARCHAR)。 如果不包括容許引數為 LONG VARCHAR 的函數簽章,則函數解析將找不到函數。

有些函數因各種原因而不容許長字串。 搭配使用 LONG VARCHAR 或 CLOB 引數與此類函數將不會成功。 例如, LONG VARCHAR 作為內建 POSSTR 函數的第二個引數,將失敗函數解析 (SQLSTATE 42884)。

具有連結運算子的表示式

在包括日文或繁體中文 EUC 資料庫伺服器的環境中,連接的其中一個運算元的潛在擴充可能會導致連接的運算元的資料類型及長度變更。 例如,在 EUC 伺服器中,來自主變數的值長度可能會加倍,請考量下列範例。
     CHAR200 CONCAT :char50

直欄 CHAR200 屬於 CHAR (200) 類型。 主變數 char50 定義為 CHAR (50)。 此連結作業的結果類型通常是 CHAR (250)。 不過,假設有 eucJP 或 eucTW 資料庫伺服器,則假設字串可能會擴充到兩倍長度。 因此 char50 會被視為 CHAR (100) ,而產生的資料類型是 VARCHAR (300)。 請注意,即使結果是 VARCHAR ,它一律會有 300 個位元組的資料,包括尾端空白。 如果不需要額外的尾端空白,請將主變數定義為 VARCHAR (50) ,而不是 CHAR (50)。

LIKE 述詞

對於涉及 EUC 資料庫中混合字串的 LIKE 述詞:
  • SBCS 半寬度底線字元參照一個 SBCS 字元。
  • 非 SBCS 全寬底線字元參照一個非 SBCS 字元。
  • SBCS 半寬或非 SBCS 全寬百分比符號字元參照零個以上 SBCS 或非 SBCS 字元。
跳出字元必須是一個 SBCS 或非 SBCS 字元。 在字元直欄中,跳出字元也可以是剛好包含一個位元組的二進位字串。

請注意,使用底線字元可能會產生不同的結果,視 LIKE 作業的字碼頁而定。 例如,日文 EUC 中的片假名字元是多位元組字元 (CS2) ,但在日文 DBCS 字碼頁中是單位元組字元。 在 pattern-expression 中具有單位元組底線的查詢會傳回日文 DBCS 伺服器中底線位置的片假名字元。 不過,不會傳回日文 EUC 伺服器中對等表格的相同列,因為片假名字元只會符合雙位元組底線。

對於涉及 EUC 資料庫中圖形字串的 LIKE 述詞:
  • 全寬底線字元 (U+FF3F) 是指一個 Unicode 字元。
  • 全寬百分比符號字元 (U+FF05) 是指零或多個 Unicode 字元。

LENGTH 函數

對於 EUC 環境中的混合字串,此函數的處理沒有不同。 傳回的值是引數字碼頁中的字串長度。 從第 8 版開始,如果引數是主變數,則傳回的值是資料庫字碼頁中字串的長度。 使用此函數來決定值的長度時,應該仔細考慮如何使用長度。 這尤其適用於混合字串常數,因為給定的長度是以位元組為單位,而不是以字元為單位。 LENGTH 函數所傳回 DBCS 資料庫中混合字串直欄的長度可能小於 eucJP 或 eucTW 用戶端上該直欄所擷取值的長度,因為將部分 DBCS 字元轉換為多位元組 eucJP 或 eucTW 字元。

SUBSTR 函數

SUBSTR 函數會以位元組為基礎對混合字串進行操作。 因此,結果字串可能在結果字串的開頭或結尾包含多位元組字元的片段。 未提供任何處理來偵測或處理字元片段。

TRANSLATE 函數

TRANSLATE 函數支援包含多位元組字元的混合字串。 to-string-expfrom-string-exp 的對應字元必須具有相同的位元組數,且不能以部分多位元組字元結尾。

char-string-exp 是字串時, pad-char-exp 必須產生單位元組字元。 由於 TRANSLATE 是以 char-string-exp的字碼頁執行,因此 pad-char-exp 可以從多位元組字元轉換為單位元組字元。

以多位元組字元部分結尾的 char-string-exp 將不會轉換那些位元組。

VARGRAPHIC 函數

日文或繁體中文 EUC 字碼頁中的字串運算元上的 VARGRAPHIC 函數會傳回 UCS-2 字碼頁中的圖形字串。
  • 單位元組字元會先轉換為其所屬字碼集中的對應雙位元組字元 (eucJP 或 eucTW)。 然後,它們會轉換為對應的 UCS-2 表示法。 如果沒有雙位元組表示法,則在轉換為 UCS-2 表示法之前,該字元會轉換為針對該字碼集定義的雙位元組替代字元。
  • 在某些編碼方法中,來自 eucJP (Katakana) 的字元 (eucJP CS2) 實際上是單位元組字元。 因此,在轉換成 UCS-2之前,它們會在 eucJP 中轉換成對應的雙位元組字元,或轉換成雙位元組替代字元。
  • 多位元組字元會轉換為其 UCS-2 表示法。

CONNECT 陳述式

成功 CONNECT 陳述式的處理會傳回 SQLCA 中的資訊,當應用程式有可能在用戶端或伺服器包含日文或繁體中文 EUC 字碼頁的環境中處理資料時,這一點很重要。 SQLERRD (1) 欄位提供從應用程式字碼頁轉換成資料庫字碼頁時,混合字串的最大擴充。 從資料庫字碼頁轉換為應用程式字碼頁時, SQLERRD (2) 欄位提供混合字串的最大擴充。 如果可能發生擴充,則值為正數; 如果可能發生縮減,則值為負數。 如果值為負數,則該值一律為 -1 ,因為最糟糕的情況是不會發生收縮,且在轉換之後需要字串的完整長度。 正值可能等於 2 ,表示在最差情況下,轉換後字串可能需要兩倍字串長度。

在 SQLCA 的 SQLERRMC 欄位中,也可以使用應用程式伺服器及應用程式用戶端的字碼頁。

PREPARE 陳述式

在包括日文或繁體中文 EUC 的環境中,不會變更針對非類型化參數標記所決定的資料類型。 因此,在某些情況下,可能需要使用類型化參數標記,為 eucJP 或 eucTW 中的混合字串提供足夠的長度。 例如,考量插入 CHAR (10) 直欄。 準備陳述式:
   INSERT INTO T1 (CH10) VALUES (?)
會導致參數標記的資料類型 CHAR (10)。 如果用戶端是 eucJP 或 eucTW ,則可能需要超過 10 個位元組才能代表要插入的字串,但資料庫 DBCS 字碼頁中的相同字串不超過 10 個位元組。 在此情況下,要準備的陳述式應該包括長度大於 10 的類型化參數標記。 因此,準備發言:
   INSERT INTO T1 (CH10) VALUES (CAST(? AS VARCHAR(20))
會導致參數標記的資料類型為 VARCHAR (20)。