MySQL知多少--字符類型

MySQL中除了數(shù)值類型外疼邀,另一個用的比較多的就是字符類型了丁鹉。字符類型有很多不同種類:VARCHAR,CHAR,BLOB,TEXT

VARCHAR

VARCHAR是變長的字符類型妒潭,實際的存儲格式如下圖所示:

img1.png

VARCHAR類型由prefixdata組成,其中prefix由一個或者兩個字節(jié)構(gòu)成揣钦,作用是指定data的長度雳灾。如果data的長度小于等于255,則prefix只需要一個字節(jié)冯凹,因為一個字節(jié)可表示的最大的無符號數(shù)就是255谎亩,如果data的長度大于255炒嘲,則prefix需要用兩個字節(jié)表示,而兩個字節(jié)可表示的最大的無符號數(shù)是65535匈庭,由此可知VARCHAR最大可以存儲65535個字符夫凸。

CHAR

CHAR是定長的字符類型,實際的存儲格式如下圖所示:

img2.png

和VARCHAR不同的是阱持,CHAR中只存儲實際的內(nèi)容夭拌,沒有用來指定長度的prefix,并且CHAR最大可存儲的字符數(shù)是255衷咽。假設(shè)一個CHAR(5)的字段鸽扁,存儲的內(nèi)容只有4個字符,那么實際存儲時會在最后加上1個空格來補齊至5個字符镶骗。而在查詢時桶现,返回的結(jié)果中末尾的空格將被移除,除非開啟了PAD_CHAR_TO_FULL_LENGTH模式鼎姊。

一個CHAR(5)的字段骡和,分配了5個字符的空間,如下圖所示:

img3.png

當(dāng)插入了abcd之后相寇,實際存儲的內(nèi)容如下圖所示:

img4.png

當(dāng)實際存儲的字符長度不足時慰于,MySQL會在末尾用空格補足。

而查詢時裆赵,實際返回的內(nèi)容中,末尾的空格又是被移除的跺嗽,如下圖所示:

img5.png

用一個實際的例子演示一下:

  • 1战授、準(zhǔn)備一張表
create table `test_c` (
 a char(5) not null,
 b varchar(5) not null
) engine=InnoDB;
  • 2、插入幾條測試數(shù)據(jù)
insert into test_c (a,b)
values 
('abcd','abcd'),
('abcd ','abcd '),
(' abcd',' abcd');
  • 3桨嫁、查詢結(jié)果
select concat("'",a,"'") as a,concat("'",b,"'") as b from test_c;
  • 4植兰、結(jié)果如下
+---------+---------+
| a       | b       |
+---------+---------+
| 'abcd'  | 'abcd'  |
| 'abcd'  | 'abcd ' |
| ' abcd' | ' abcd' |
+---------+---------+

可以發(fā)現(xiàn)查詢時,返回的結(jié)果中末尾的空格都被移除了璃吧,不管末尾的空格是不是我們實際存儲的值楣导。那這種情況下就會出現(xiàn)問題,實際我們是需要末尾的空格的畜挨,但查詢的結(jié)果末尾的空格被移除了筒繁。解決的方法是,開啟PAD_CHAR_TO_FULL_LENGTH的SQL Mode巴元。

  • 1毡咏、先查一下當(dāng)前的SQL Mode:
select @@sql_mode;

結(jié)果如下:

+--------------------------------------------+
| @@sql_mode                                 |
+--------------------------------------------+
| STRICT_TRANS_TABLES,NO_ENGINE_SUBSTITUTION |
+--------------------------------------------+
  • 2、設(shè)置SQL Mode:
SET sql_mode=`PAD_CHAR_TO_FULL_LENGTH`;
  • 3逮刨、再查詢結(jié)果:
select concat("'",a,"'") as a,concat("'",b,"'") as b from test_c;
  • 4呕缭、結(jié)果如下:
+---------+---------+
| a       | b       |
+---------+---------+
| 'abcd ' | 'abcd'  |
| 'abcd ' | 'abcd ' |
| ' abcd' | ' abcd' |
+---------+---------+

可以看到,設(shè)置了PAD_CHAR_TO_FULL_LENGTH的SQL Mode之后,CHAR類型的字段末尾的空格沒有被移除恢总。

存儲的長度超限

當(dāng)存儲的字符長度超過了CHAR和VARCHAR設(shè)置的長度迎罗,在不同的情況下會有不同的效果。在嚴(yán)格模式下片仿,超過長度的字符是不能保存成功的纹安,系統(tǒng)會報錯。在非嚴(yán)格模式下滋戳,能保存成功钻蔑,CHAR類型的會截斷超過長度的部分,并且不會有任何反映奸鸯,VARCHAR類型的也會截斷超過長度的部分咪笑,但是會拋出警告。

PS:
需要注意的是娄涩,CHAR和VARCHAR中存儲的內(nèi)容的長度是指的字符長度窗怒,不是字節(jié)長度,而字符長度跟選擇的字符集有關(guān)蓄拣,比如ASCII字符集可以存儲英文和數(shù)字等扬虚,不能存儲中文,因為一個中文字符占3個字節(jié)球恤,UTF8字符集就可以存儲中文了辜昵,但是UTF8不能存儲emoji表情,因為emoji表情占4個字節(jié)咽斧,而UTF8MB4就可以存儲emoji表情堪置。

CHAR和VARCHAR的區(qū)別:

比較維度 CHAR VARCHAR
組成結(jié)構(gòu) data prefix+data
最低存儲需求 0字節(jié) 1字節(jié)
最大長度 255 65535
存儲時長度不足 末尾用空格補齊 不補齊
存儲時長度超限(非嚴(yán)格模式) 截斷并且靜默 截斷并且警告
存儲時長度超限(嚴(yán)格模式) 報錯并且不能保存 報錯并且不能保存
查詢時(無PAD_CHAR_TO_FULL_LENGTH) 移除末尾空格 不移除末尾空格
查詢時(有PAD_CHAR_TO_FULL_LENGTH) 不移除末尾空格 不移除末尾空格

BLOB和TEXT

BLOB和TEXT主要是用來存儲數(shù)據(jù)長度非常大的字符類型的,BLOB主要是存儲二進制字符類型张惹,TEXT則是存儲字符串舀锨。
其中BLOB又包括了TINYBLOB,SMALLBLOB,MEDIUNBLOB,LONGBLOB,TEXT包括了TINYTEXT,SMALLTEXT,MEDIUNTEXT,LONGTEXTB

當(dāng)BLOB和TEXT的值太大時宛逗,InnoDB會使用專門的外部存儲區(qū)域來存儲坎匿,這時就會在字段中用一個1~4個字節(jié)的指針,紀(jì)錄下外部實際存儲的區(qū)域雷激。
MySQL對BLOB和TEXT類型的字段進行排序時替蔬,只會對字段的前max_sort_length個字節(jié)的內(nèi)容而不是整個內(nèi)容進行排序。

我是逅弈屎暇,如果文章對您有幫助进栽,歡迎您點贊加關(guān)注,并歡迎您關(guān)注我的公眾號:

歡迎關(guān)注微信公眾號
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末恭垦,一起剝皮案震驚了整個濱河市快毛,隨后出現(xiàn)的幾起案子格嗅,更是在濱河造成了極大的恐慌,老刑警劉巖唠帝,帶你破解...
    沈念sama閱讀 219,366評論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件屯掖,死亡現(xiàn)場離奇詭異,居然都是意外死亡襟衰,警方通過查閱死者的電腦和手機贴铜,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,521評論 3 395
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來瀑晒,“玉大人绍坝,你說我怎么就攤上這事√υ茫” “怎么了轩褐?”我有些...
    開封第一講書人閱讀 165,689評論 0 356
  • 文/不壞的土叔 我叫張陵,是天一觀的道長玖详。 經(jīng)常有香客問我把介,道長,這世上最難降的妖魔是什么蟋座? 我笑而不...
    開封第一講書人閱讀 58,925評論 1 295
  • 正文 為了忘掉前任拗踢,我火速辦了婚禮,結(jié)果婚禮上向臀,老公的妹妹穿的比我還像新娘巢墅。我一直安慰自己,他們只是感情好券膀,可當(dāng)我...
    茶點故事閱讀 67,942評論 6 392
  • 文/花漫 我一把揭開白布君纫。 她就那樣靜靜地躺著,像睡著了一般三娩。 火紅的嫁衣襯著肌膚如雪庵芭。 梳的紋絲不亂的頭發(fā)上妹懒,一...
    開封第一講書人閱讀 51,727評論 1 305
  • 那天雀监,我揣著相機與錄音,去河邊找鬼眨唬。 笑死会前,一個胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的匾竿。 我是一名探鬼主播瓦宜,決...
    沈念sama閱讀 40,447評論 3 420
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼岭妖!你這毒婦竟也來了临庇?” 一聲冷哼從身側(cè)響起反璃,我...
    開封第一講書人閱讀 39,349評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎假夺,沒想到半個月后淮蜈,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,820評論 1 317
  • 正文 獨居荒郊野嶺守林人離奇死亡已卷,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,990評論 3 337
  • 正文 我和宋清朗相戀三年梧田,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片侧蘸。...
    茶點故事閱讀 40,127評論 1 351
  • 序言:一個原本活蹦亂跳的男人離奇死亡裁眯,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出讳癌,到底是詐尸還是另有隱情穿稳,我是刑警寧澤,帶...
    沈念sama閱讀 35,812評論 5 346
  • 正文 年R本政府宣布析桥,位于F島的核電站司草,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏泡仗。R本人自食惡果不足惜埋虹,卻給世界環(huán)境...
    茶點故事閱讀 41,471評論 3 331
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望娩怎。 院中可真熱鬧搔课,春花似錦、人聲如沸截亦。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,017評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽崩瓤。三九已至袍啡,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間却桶,已是汗流浹背境输。 一陣腳步聲響...
    開封第一講書人閱讀 33,142評論 1 272
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留颖系,地道東北人嗅剖。 一個月前我還...
    沈念sama閱讀 48,388評論 3 373
  • 正文 我出身青樓,卻偏偏與公主長得像嘁扼,于是被迫代替她去往敵國和親信粮。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 45,066評論 2 355

推薦閱讀更多精彩內(nèi)容