最近在線上發(fā)現(xiàn)了一個很奇怪的現(xiàn)象永丝,聯(lián)合查詢沒有命中索引琉预。通過網(wǎng)上查找一些資料玉罐,有人建議查看所關(guān)聯(lián)的字段的數(shù)據(jù)格式是不是一致因惭,通過排查發(fā)現(xiàn)了數(shù)據(jù)庫的兩個表的character 以及collation設(shè)置的不同岳锁。
ALTER TABLE table MODIFY colunm varchar(50) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL DEFAULT '' COMMENT 'comment';
更改后在聯(lián)表查詢數(shù)據(jù)庫報錯 Illegal mix of collations 。
下面簡單介紹一下mysql 的 collation蹦魔,內(nèi)容來自于mysql官網(wǎng)的相關(guān)介紹 https://dev.mysql.com/doc/refman/5.7/en/charset-general.html激率。
http://dev.mysql.com/doc/en/charset-collation-effect.html
http://dev.mysql.com/doc/en/charset-collation-expressions.html
stackoverflow 上的資料
https://stackoverflow.com/questions/3029321/troubleshooting-illegal-mix-of-collations-error-in-mysql
Character Sets是字符和編碼咳燕。collation是編碼的校驗規(guī)格,包括比較和排序乒躺。舉例說就是 字符串AB 迟郎,對用的字符就是AB, 編碼是01聪蘸。collation就是對01的比較宪肖。如果collation是大小寫不敏感的,那么首先先把a(bǔ)b 和AB等同對待健爬,然后比較編碼
每一種 Character Sets 對應(yīng)至少一種collation
兩種不同的Character Sets 不會有相同的collation
當(dāng)一種Character Sets 對應(yīng)不同的校驗規(guī)則的時候控乾,找到一個最合適的規(guī)則可能就不是那么容易。由此就引入了字符集的概念娜遵,使不同的效驗規(guī)則都對應(yīng)特定的字符集蜕衡,這樣既是規(guī)則不同,也能選用一個相對合乎情理的規(guī)則设拟。
字符串就有字符集的屬性慨仿,字符集包含兩種,UNICODE和
ASCII纳胧。ASCII是UNICODE的子集镰吆,mysql就可以自此基礎(chǔ)上作對應(yīng)的轉(zhuǎn)換,如果沒有合法的轉(zhuǎn)換跑慕,就會拋出“illegal mix of collations” 的異常万皿。
然后介紹一下Collation的命名規(guī)范
到此就可以看出來 Illegal mix of collations 的異常,是和字符集相關(guān)核行。
如果有確定的交驗規(guī)則牢硅,需要驗證比較規(guī)則是否能夠通用。
有兩個重要的原則
- 如果都是Unicode或者都不是Unicode 拋出異常芝雪。
- 如果一方是Unicode减余,一方不是,則按照Unicode比較
最后的修改方式也比較粗暴惩系,修改成相同的collation位岔,問題解決了。