跨資料庫、跨伺服器查詢時,若聯結欄位排序規則不同,會拋出「無法解決排序規則衝突」錯誤。本文系統解析 Collation 名稱結構、衝突觸發條件,提供三種解決方案(查詢層指定、資料庫層統一、欄位層修改),並附最佳實務建議。
Collation 定義:
Chinese_PRC_CI_AI_WS
│ │ │ │
│ │ │ └─ WS: 寬度敏感 (Width Sensitive) / WI: 不敏感
│ │ └──── AI: 重音不敏感 (Accent Insensitive) / AS: 敏感
│ └────── CI: 大小寫不敏感 (Case Insensitive) / CS: 敏感
└───────────────── 語言/字元集:Chinese_PRC (大陸簡體)
| 後綴 | 含義 | 說明 |
|---|---|---|
| _BIN | 二進位排序 (相容) | 依碼位比較,效能最好但不符合語言習慣 |
| _BIN2 | 二進位排序 (SQL 2005+) | 碼位比較語義,效能佳 |
| _Stroke | 筆畫排序 | 中文筆畫序 |
| _CI / _CS | 大小寫不敏感/敏感 | |
| _AI / _AS | 重音不敏感/敏感 | |
| _KI / _KS | 假名類型不敏感/敏感 | 日文平/片假名 |
| _WI / _WS | 全半角不敏感/敏感 |
CREATE TABLE TagsTableA (TagName NVARCHAR(64) COLLATE Chinese_PRC_BIN);
CREATE TABLE TagsTableB (TagName NVARCHAR(64) COLLATE Chinese_PRC_CI_AS);
SELECT * FROM TagsTableA A INNER JOIN TagsTableB B ON A.TagName = B.TagName;
-- 錯誤:無法解決 "Chinese_PRC_BIN" 和 "Chinese_PRC_CI_AS" 之間的排序規則衝突
SELECT * FROM TagsTableA A
INNER JOIN TagsTableB B
ON A.TagName COLLATE Chinese_PRC_CI_AS = B.TagName; -- 強制統一
-- 僅影響後續建立的資料表/欄位,現有物件不變
ALTER DATABASE MyDB COLLATE Chinese_PRC_CI_AS;
ALTER TABLE TagsTableA ALTER COLUMN TagName NVARCHAR(64) COLLATE Chinese_PRC_CI_AS;
Chinese_PRC_CI_AS 或 Latin1_General_CI_AS)。SELECT ... INTO 新表 重建法。建立統一 Collation 規範並納入程式碼審查,能從源頭杜絕排序規則衝突,避免上線後緊急修補帶來的風險與停機。