若要為 Unicode 字元集新增 UCA 校對,而無需重新編譯 MySQL,請使用以下程序。如果您不熟悉用於描述校對排序特性的 LDML 規則,請參閱第 12.14.4.2 節,「MySQL 中支援的 LDML 語法」。
此範例將名為 utf8mb4_phone_ci
的校對新增至 utf8mb4
字元集。此校對是為涉及使用者張貼其姓名和電話號碼的 Web 應用程式情境所設計。電話號碼可以使用非常不同的格式提供
+7-12345-67
+7-12-345-67
+7 12 345 67
+7 (12) 345 67
+71234567
處理這些種類的值所產生的問題是,不同的允許格式使得搜尋特定電話號碼非常困難。解決方案是定義一個新的校對,重新排序標點符號字元,使其可忽略。
選擇校對 ID,如第 12.14.2 節,「選擇校對 ID」所示。以下步驟使用 ID 1029。
修改
Index.xml
組態檔。此檔案位於由character_sets_dir
系統變數所指定的目錄中。您可以如下所示檢查變數值,儘管您系統上的路徑名稱可能不同mysql> SHOW VARIABLES LIKE 'character_sets_dir'; +--------------------+-----------------------------------------+ | Variable_name | Value | +--------------------+-----------------------------------------+ | character_sets_dir | /user/local/mysql/share/mysql/charsets/ | +--------------------+-----------------------------------------+
選擇校對的名稱,並在
Index.xml
檔案中列出。此外,您必須提供校對排序規則。尋找要新增校對之字元集的<charset>
元素,並新增一個<collation>
元素,指示校對名稱和 ID,以將名稱與 ID 關聯。在<collation>
元素內,提供一個包含排序規則的<rules>
元素<charset name="utf8mb4"> ... <collation name="utf8mb4_phone_ci" id="1029"> <rules> <reset>\u0000</reset> <i>\u0020</i> <!-- space --> <i>\u0028</i> <!-- left parenthesis --> <i>\u0029</i> <!-- right parenthesis --> <i>\u002B</i> <!-- plus --> <i>\u002D</i> <!-- hyphen --> </rules> </collation> ... </charset>
如果您想要其他 Unicode 字元集有類似的校對,請新增其他
<collation>
元素。例如,若要定義ucs2_phone_ci
,請將<collation>
元素新增至<charset name="ucs2">
元素。請記住,每個校對都必須有其自己唯一的 ID。重新啟動伺服器,並使用此陳述式驗證校對是否存在
mysql> SHOW COLLATION WHERE Collation = 'utf8mb4_phone_ci'; +------------------+---------+------+---------+----------+---------+ | Collation | Charset | Id | Default | Compiled | Sortlen | +------------------+---------+------+---------+----------+---------+ | utf8mb4_phone_ci | utf8mb4 | 1029 | | | 8 | +------------------+---------+------+---------+----------+---------+
現在測試校對,以確保它具有所需的屬性。
使用新的校對建立一個包含一些範例電話號碼的表格
mysql> CREATE TABLE phonebook (
name VARCHAR(64),
phone VARCHAR(64) CHARACTER SET utf8mb4 COLLATE utf8mb4_phone_ci
);
Query OK, 0 rows affected (0.09 sec)
mysql> INSERT INTO phonebook VALUES ('Svoj','+7 912 800 80 02');
Query OK, 1 row affected (0.00 sec)
mysql> INSERT INTO phonebook VALUES ('Hf','+7 (912) 800 80 04');
Query OK, 1 row affected (0.00 sec)
mysql> INSERT INTO phonebook VALUES ('Bar','+7-912-800-80-01');
Query OK, 1 row affected (0.00 sec)
mysql> INSERT INTO phonebook VALUES ('Ramil','(7912) 800 80 03');
Query OK, 1 row affected (0.00 sec)
mysql> INSERT INTO phonebook VALUES ('Sanja','+380 (912) 8008005');
Query OK, 1 row affected (0.00 sec)
執行一些查詢,看看用於比較和排序的忽略標點符號字元是否實際上被忽略
mysql> SELECT * FROM phonebook ORDER BY phone;
+-------+--------------------+
| name | phone |
+-------+--------------------+
| Sanja | +380 (912) 8008005 |
| Bar | +7-912-800-80-01 |
| Svoj | +7 912 800 80 02 |
| Ramil | (7912) 800 80 03 |
| Hf | +7 (912) 800 80 04 |
+-------+--------------------+
5 rows in set (0.00 sec)
mysql> SELECT * FROM phonebook WHERE phone='+7(912)800-80-01';
+------+------------------+
| name | phone |
+------+------------------+
| Bar | +7-912-800-80-01 |
+------+------------------+
1 row in set (0.00 sec)
mysql> SELECT * FROM phonebook WHERE phone='79128008001';
+------+------------------+
| name | phone |
+------+------------------+
| Bar | +7-912-800-80-01 |
+------+------------------+
1 row in set (0.00 sec)
mysql> SELECT * FROM phonebook WHERE phone='7 9 1 2 8 0 0 8 0 0 1';
+------+------------------+
| name | phone |
+------+------------------+
| Bar | +7-912-800-80-01 |
+------+------------------+
1 row in set (0.00 sec)