MySQL默認(rèn)字符集設(shè)置詳情
查看各版本默認(rèn)字符集
在MySQL 8.0版本之前,默認(rèn)字符集為latin1
,utf8字符集指向的是utf8mb3 。網(wǎng)站開(kāi)發(fā)人員在數(shù)據(jù)庫(kù)設(shè)計(jì)的時(shí)候往往會(huì)將編碼修改為utf8字符集。如果遺忘修改默認(rèn)的編碼,就會(huì)出現(xiàn)亂碼的問(wèn)題。從MySQL8.0開(kāi)始,數(shù)據(jù)庫(kù)的默認(rèn)編碼將改為utf8mb4 ,從而避免上述亂碼的問(wèn)題。
使用以下命令可以查看MySQL的默認(rèn)字符集:
show variables like 'character%'; # 或者 show variables like '%char%';
MySQL:8.0.30 中執(zhí)行:
- MySQL:5.7.29 中執(zhí)行
參數(shù)解釋:
#服務(wù)器級(jí)別的默認(rèn)字符集,創(chuàng)建數(shù)據(jù)庫(kù)沒(méi)有顯示的指定字符集就使用該級(jí)別的默認(rèn)字符集 character_set_server=latin1 #數(shù)據(jù)庫(kù)級(jí)別的默認(rèn)字符集,創(chuàng)建表沒(méi)有顯示的指定字符集就使用該級(jí)別的默認(rèn)字符集 character_set_database=latin1
修改MySQL5中的默認(rèn)字符集
因?yàn)槲业腗ySQL是docker部署,所以修改方式略微有一些不一樣
先查看容器ID:
docker ps
根據(jù)容器ID進(jìn)入容器:
docker exec -it e14 /bin/bash
進(jìn)入 /etc/mysql/mysql.conf.d/
目錄
cd /etc/mysql/mysql.conf.d/
- 因?yàn)閐ocker容器內(nèi)未安裝vim,所以需要先安裝vim
#使用國(guó)內(nèi)鏡像 ? cp /etc/apt/sources.list /etc/apt/sources.list.bak ? echo "" > /etc/apt/sources.list echo "deb http://mirrors.aliyun.com/debian buster main" >> /etc/apt/sources.list ; echo "deb http://mirrors.aliyun.com/debian-security buster/updates main" >> /etc/apt/sources.list ; echo "deb http://mirrors.aliyun.com/debian buster-updates main" >> /etc/apt/sources.list;
更新apt-get指令:
apt-get update
安裝vim:
apt-get install ?vim
在上面的目錄下編輯mysqld.cnf:
vim mysqld.cnf
插入如下內(nèi)容:
character_set_server=utf8
- 重啟容器
- 再次進(jìn)入容器查看默認(rèn)編碼
但是原庫(kù)、原表的設(shè)定不會(huì)發(fā)生變化,參數(shù)修改只對(duì)新建的數(shù)據(jù)庫(kù)生效。
已有庫(kù)&表字符集的變更
MySQL5.7版本中,以前創(chuàng)建的庫(kù),創(chuàng)建的表字符集還是latin1
修改已創(chuàng)建數(shù)據(jù)庫(kù)的字符集:
alter database dbtest1 character set 'utf8';
修改已創(chuàng)建數(shù)據(jù)表的字符集:
alter table t_emp convert to character set 'utf8';
注意:但是原有的數(shù)據(jù)如果是用非'utf8'編碼的話,數(shù)據(jù)本身編碼不會(huì)發(fā)生改變。已有數(shù)據(jù)需要導(dǎo) 出或刪除,然后重新插入。
各級(jí)別的字符集
MySQL有4個(gè)級(jí)別的字符集和比較規(guī)則,分別是:
- 服務(wù)器級(jí)別
- 數(shù)據(jù)庫(kù)級(jí)別
- 標(biāo)級(jí)別
- 列級(jí)別
執(zhí)行如下SQL語(yǔ)句:
show variables like 'character%';
character_set_server
:服務(wù)器級(jí)別的字符集character_set_database
:當(dāng)前數(shù)據(jù)庫(kù)的字符集character_set_client
:服務(wù)器解碼請(qǐng)求時(shí)使用的字符集character_set_connection
:服務(wù)器處理請(qǐng)求時(shí)會(huì)把請(qǐng)求字符串從character_set_client
轉(zhuǎn)為character_set_connection
character_set_results
:服務(wù)器向客戶端返回?cái)?shù)據(jù)時(shí)使用的字符集
我們介紹的這4個(gè)級(jí)別字符集和比較規(guī)則的聯(lián)系如下:
- 如果創(chuàng)建或修改列時(shí)沒(méi)有顯式的指定字符集和比較規(guī)則,則該列默認(rèn)用表的字符集和比較規(guī)則
- 如果創(chuàng)建表時(shí)沒(méi)有顯式的指定字符集和比較規(guī)則,則該表默認(rèn)用數(shù)據(jù)庫(kù)的字符集和比較規(guī)則
- 如果創(chuàng)建數(shù)據(jù)庫(kù)時(shí)沒(méi)有顯式的指定字符集和比較規(guī)則,則該數(shù)據(jù)庫(kù)默認(rèn)用服務(wù)器的字符集和比較規(guī) 則
字符集與比較規(guī)則
utf8 與 utf8mb4
utf8 字符集表示一個(gè)字符需要使用1~4個(gè)字節(jié),但是我們常用的一些字符使用1~3個(gè)字節(jié)就可以表示了。而字符集表示一個(gè)字符所用的最大字節(jié)長(zhǎng)度,在某些方面會(huì)影響系統(tǒng)的存儲(chǔ)和性能,所以設(shè)計(jì)MySQL的設(shè)計(jì)者偷偷的定義了兩個(gè)概念:
- utf8mb3 :閹割過(guò)的utf8 字符集,只使用1~3個(gè)字節(jié)表示字符(表情符號(hào)等會(huì)亂碼)
- utf8mb4 :正宗的utf8 字符集,使用1~4個(gè)字節(jié)表示字符
比較規(guī)則
MySQL版本一共支持41種字符集,其中的Default collation 列表示這種字符集中一種默認(rèn)的比較規(guī)則,里面包含著該比較規(guī)則主要作用于哪種語(yǔ)言,比如utf8_polish_ci 表示以波蘭語(yǔ)的規(guī)則比較, utf8_spanish_ci 是以西班牙語(yǔ)的規(guī)則比較, utf8_general_ci 是一種通用的比較規(guī)則。后綴表示該比較規(guī)則是否區(qū)分語(yǔ)言中的重音、大小寫。具體如下:
常用操作:
#查看GBK字符集的比較規(guī)則 SHOW COLLATION LIKE 'gbk%'; #查看UTF-8字符集的比較規(guī)則 SHOW COLLATION LIKE 'utf8%'; #查看服務(wù)器的字符集和比較規(guī)則 SHOW VARIABLES LIKE '%_server'; #查看數(shù)據(jù)庫(kù)的字符集和比較規(guī)則 SHOW VARIABLES LIKE '%_database'; #查看具體數(shù)據(jù)庫(kù)的字符集 SHOW CREATE DATABASE dbtest1; #修改具體數(shù)據(jù)庫(kù)的字符集 ALTER DATABASE dbtest1 DEFAULT CHARACTER SET 'utf8' COLLATE 'utf8_general_ci'; #查看表的字符集 show create table employees; #查看表的比較規(guī)則 show table status from atguigudb like 'employees'; #修改表的字符集和比較規(guī)則 ALTER TABLE emp1 DEFAULT CHARACTER SET 'utf8' COLLATE 'utf8_general_ci';
請(qǐng)求到響應(yīng)過(guò)程中字符集的變化
系統(tǒng)變量 | 描述 |
---|---|
character_set_client | 服務(wù)器解碼請(qǐng)求時(shí)使用的字符集 |
character_set_connection | 服務(wù)器處理請(qǐng)求時(shí)會(huì)把請(qǐng)求字符串從character_set_client 轉(zhuǎn)為character_set_connection |
character_set_results | 服務(wù)器向客戶端返回?cái)?shù)據(jù)時(shí)使用的字符集 |
這幾個(gè)系統(tǒng)變量在我的計(jì)算機(jī)上的默認(rèn)值如下(不同操作系統(tǒng)的默認(rèn)值可能不同,MySQL版本:8.0.30):
字符集在請(qǐng)求處理過(guò)程中的變化:
SQL大小寫規(guī)范
Windows和Linux平臺(tái)區(qū)別
在 SQL 中,關(guān)鍵字和函數(shù)名是不用區(qū)分字母大小寫的,比如 SELECT、WHERE、ORDER、GROUP BY 等關(guān)鍵字,以及 ABS、MOD、ROUND、MAX 等函數(shù)名。
不過(guò)在 SQL 中,你還是要確定大小寫的規(guī)范,因?yàn)樵?Linux 和 Windows 環(huán)境下,你可能會(huì)遇到不同的大小寫問(wèn)題。windows系統(tǒng)默認(rèn)大小寫不敏感,但是linux系統(tǒng)是大小寫敏感的。
通過(guò)如下命令查看:
SHOW VARIABLES LIKE '%lower_case_table_names%';
Windows系統(tǒng)下:
Linux系統(tǒng)下:
lower_case_table_names
參數(shù)值的設(shè)置:
- 默認(rèn)為0,大小寫敏感
- 設(shè)置1,大小寫不敏感。創(chuàng)建的表,數(shù)據(jù)庫(kù)都是以小寫形式存放在磁盤上,對(duì)于sql語(yǔ)句都是轉(zhuǎn)換為小寫對(duì)表和數(shù)據(jù)庫(kù)進(jìn)行查找
- 設(shè)置2,創(chuàng)建的表和數(shù)據(jù)庫(kù)依據(jù)語(yǔ)句上格式存放,凡是查找都是轉(zhuǎn)換為小寫進(jìn)行
MySQL在Linux下數(shù)據(jù)庫(kù)名、表名、列名、別名大小寫規(guī)則是這樣的:
數(shù)據(jù)庫(kù)名、表名、表的別名、變量名是嚴(yán)格區(qū)分大小寫的
關(guān)鍵字、函數(shù)名稱在 SQL 中不區(qū)分大小寫
列名(或字段名)與列的別名(或字段別名)在所有的情況下均是忽略大小寫的
MySQL在Windows的環(huán)境下全部不區(qū)分大小寫
Linux下大小寫規(guī)則設(shè)置:
當(dāng)想設(shè)置為大小寫不敏感時(shí),要在my.cnf 這個(gè)配置文件 [mysqld] 中加入lower_case_table_names=1 ,然后重啟服務(wù)器
- 但是要在重啟數(shù)據(jù)庫(kù)實(shí)例之前就需要將原來(lái)的數(shù)據(jù)庫(kù)和表轉(zhuǎn)換為小寫,否則將找不到數(shù)據(jù)庫(kù)名
- 此參數(shù)適用于MySQL5.7 ,在MySQL8 下禁止在重新啟動(dòng)
MySQL
服務(wù)時(shí)將lower_case_table_names
設(shè)置成不同于初始化 MySQL 服務(wù)時(shí)設(shè)置的lower_case_table_names
值
SQL編寫建議
如果你的變量名命名規(guī)范沒(méi)有統(tǒng)一,就可能產(chǎn)生錯(cuò)誤。
這里有一個(gè)有關(guān)命名規(guī)范的建議:
- 關(guān)鍵字和函數(shù)名稱全部大寫
- 數(shù)據(jù)庫(kù)名、表名、表別名、字段名、字段別名等全部小寫
- SQL 語(yǔ)句必須以分號(hào)結(jié)尾
數(shù)據(jù)庫(kù)名、表名和字段名在 Linux MySQL 環(huán)境下是區(qū)分大小寫的,因此建議你統(tǒng)一這些字段的命名規(guī)則,比如全部采用小寫的方式
雖然關(guān)鍵字和函數(shù)名稱在 SQL 中不區(qū)分大小寫,也就是如果小寫的話同樣可以執(zhí)行。但是同時(shí)將關(guān)鍵詞和函數(shù)名稱全部大寫,以便于區(qū)分?jǐn)?shù)據(jù)庫(kù)名、表名、字段名
sql_mode的合理設(shè)置
寬松模式
如果設(shè)置的是寬松模式,那么我們?cè)诓迦霐?shù)據(jù)的時(shí)候,即便是給了一個(gè)錯(cuò)誤的數(shù)據(jù),也可能會(huì)被接受,并且不報(bào)錯(cuò)。
舉例:我在創(chuàng)建一個(gè)表時(shí),該表中有一個(gè)字段為name,給name設(shè)置的字段類型時(shí)char(10) ,如果我在插入數(shù)據(jù)的時(shí)候,其中name這個(gè)字段對(duì)應(yīng)的有一條數(shù)據(jù)的長(zhǎng)度超過(guò)了10 ,例如'1234567890abc',超過(guò)了設(shè)定的字段長(zhǎng)度10,那么不會(huì)報(bào)錯(cuò),并且取前10個(gè)字符存上,也就是說(shuō)你這個(gè)數(shù)據(jù)被存為了'1234567890',而'abc'就沒(méi)有了。但是,我們給的這條數(shù)據(jù)是錯(cuò)誤的,因?yàn)槌^(guò)了字段長(zhǎng)度,但是并沒(méi)有報(bào)錯(cuò),并且mysql自行處理并接受了,這就是寬松模式的效果。
應(yīng)用場(chǎng)景:通過(guò)設(shè)置sql mode為寬松模式,來(lái)保證大多數(shù)sql符合標(biāo)準(zhǔn)的sql語(yǔ)法,這樣應(yīng)用在不同數(shù)據(jù)庫(kù)之間進(jìn)行遷移時(shí),則不需要對(duì)業(yè)務(wù)sql 進(jìn)行較大的修改。
嚴(yán)格模式
出現(xiàn)上面寬松模式的錯(cuò)誤,應(yīng)該報(bào)錯(cuò)才對(duì),所以MySQL5.7版本就將sql_mode默認(rèn)值改為了嚴(yán)格模式。所以在生產(chǎn)等環(huán)境中,我們必須采用的是嚴(yán)格模式,進(jìn)而開(kāi)發(fā)、測(cè)試環(huán)境的數(shù)據(jù)庫(kù)也必須要設(shè)置,這樣在開(kāi)發(fā)測(cè)試階段就可以發(fā)現(xiàn)問(wèn)題。并且我們即便是用的MySQL5.6,也應(yīng)該自行將其改為嚴(yán)格模式。
開(kāi)發(fā)經(jīng)驗(yàn):MySQL等數(shù)據(jù)庫(kù)總想把關(guān)于數(shù)據(jù)的所有操作都自己包攬下來(lái),包括數(shù)據(jù)的校驗(yàn),其實(shí)開(kāi)發(fā)中,我們應(yīng)該在自己開(kāi)發(fā)的項(xiàng)目程序級(jí)別將這些校驗(yàn)給做了,雖然寫項(xiàng)目的時(shí)候麻煩了一些步驟,但是這樣做之后,我們?cè)谶M(jìn)行數(shù)據(jù)庫(kù)遷移或者在項(xiàng)目的遷移時(shí),就會(huì)方便很多。
筆記源于視頻教程:MySQL數(shù)據(jù)庫(kù)教程天花板,mysql安裝到mysql高級(jí),強(qiáng)!硬!
到此這篇關(guān)于MySQL默認(rèn)字符集設(shè)置詳情的文章就介紹到這了,更多相關(guān)MySQL默認(rèn)字符集 內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
mysql數(shù)據(jù)庫(kù)如何實(shí)現(xiàn)億級(jí)數(shù)據(jù)快速清理
這篇文章主要介紹了mysql數(shù)據(jù)庫(kù)實(shí)現(xiàn)億級(jí)數(shù)據(jù)快速清理的方法,非常不錯(cuò),具有參考借鑒價(jià)值,需要的朋友參考下吧2018-04-04MySql判斷漢字、日期、數(shù)字的具體函數(shù)
這篇文章主要大家詳細(xì)介紹了MySql判斷漢字、日期、數(shù)字的具體函數(shù),感興趣的小伙伴們可以參考一下2016-05-05MySQL提示:The server quit without updating
今天網(wǎng)站web頁(yè)面提交內(nèi)容到數(shù)據(jù)庫(kù),發(fā)現(xiàn)出錯(cuò)了,一直提交不了,數(shù)找了下原因,發(fā)現(xiàn)數(shù)據(jù)寫不進(jìn)去!第一反應(yīng),重啟mysql數(shù)據(jù)庫(kù),一直執(zhí)行中,停止不了也啟動(dòng)不了,直覺(jué)告訴我磁盤滿了 !2014-04-04Mysql系列SQL查詢語(yǔ)句書寫順序及執(zhí)行順序詳解
這篇文章主要為大家介紹了Mysql系列SQL查詢語(yǔ)句的書寫順序及執(zhí)行順序示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步2021-10-10Mysql存儲(chǔ)過(guò)程中游標(biāo)的用法實(shí)例
這篇文章主要介紹了Mysql存儲(chǔ)過(guò)程中游標(biāo)的用法,以商戶關(guān)聯(lián)數(shù)據(jù)的插入及更新為例分析了MySQL存儲(chǔ)過(guò)程中游標(biāo)的使用技巧,需要的朋友可以參考下2015-07-07