MySQL类型介绍以及适用范围
1. 整型類型
Tinyint(8位)
范圍:無符號(0~256)、有符號(-128~127)
場景:一般用于存儲數(shù)字字典,常量表的id,因為數(shù)據(jù)量十分有限,又是常量表,所以可以用它存儲
Smallint(16位)
范圍:無符號(0~65536)、有符號(-32768~32767)
場景:Tinyint的替代品,若常量表數(shù)據(jù)比較多,比如中國的省-市-自治區(qū)-區(qū)縣-村鎮(zhèn),到這個范圍下,基本夠用了。中國有65536個村鎮(zhèn)(區(qū)縣)嗎?
Mediumint(24位)
范圍:無符號(0~16777216)、有符號(-8388608~8388607)
場景:1000w以內(nèi)的數(shù)據(jù),這個若是日志表,又是在一段時間內(nèi)數(shù)據(jù)量可控,定時清理,Mediumint不失為是輕量級的int的一種id選擇。
Int(32位):大多數(shù)場景,一般Java的int也支持不了這么長的整數(shù)位!
范圍:無符號(0~4294967296)、有符號(-2147483648~2147483647)
場景:大多數(shù)的自增id場景,基本夠用了。無符號40多億數(shù)據(jù),一般的中小型,互聯(lián)網(wǎng),基本夠用。
Bigint(64位)范圍:天文數(shù)字,在Java中必須特殊處理該數(shù)字類型——BigDecimal進(jìn)行處理。
范圍:無符號(0~18446744073709551616)、有符號(-922337203685478~922337203685477)。
場景:使用關(guān)系型數(shù)據(jù)庫存儲海量數(shù)據(jù)的id。千萬大一位是億,億大一位是兆,兆在大一位是什么????不過數(shù)據(jù)量在這個范圍,很難想象還用RDBMS進(jìn)行管理。
有符號與無符號的最大區(qū)別就是是否支持負(fù)數(shù)。Unsigned一旦被選擇上了,表示不允許負(fù)數(shù),也就是存儲無符號數(shù)。一般情況下無符號int類型的字段幾乎可以滿足系統(tǒng)要求了,就算是自增id類型。40多億的mysql數(shù)據(jù)量也已經(jīng)比較不小了。日交易量記錄上千萬比記錄,一個月也就區(qū)區(qū)3億記錄。如果大于這個數(shù)量級的數(shù)據(jù),又是實時數(shù)據(jù),應(yīng)該考慮分表分庫。或者借助NoSQL,將數(shù)據(jù)量散列拆分開。扯遠(yuǎn)了,這里就是告訴大家,數(shù)值類型字段支持的范圍。
2. 實數(shù)類型
其實基本上也就是指含有小數(shù)的數(shù),也就是浮點類型的數(shù)據(jù)類型。
Float:4個字節(jié)存儲
Double:8個字節(jié)存儲
Decimal:允許65個數(shù)字
這里有位仁兄總結(jié)的浮點型和定點型計算的文章,很不錯http://www.163ns.com/zixun/post/5226.html。
基本上float可以用作百分比,有點誤差沒關(guān)系,double精確度比float大。而Decimal是完全金額類型計算。有的非敏感的,金額不是特別精確的系統(tǒng)業(yè)務(wù)場景,筆者也見過也有人使用double的。(你說那些不精確的,被四舍的錢都哪去了,都?xì)w誰了?100個人也就算了,如果涉及到1000w個人,每個人被四舍了的幾厘錢,甚至到分錢誤差,加起來夠買房子了吧?)
3. 字符串類型
字符串類型主要分為varchar、char與blob、text之間的PK了。
一定要將字符串類型的字段調(diào)優(yōu)到極致,因為數(shù)據(jù)庫中,我們面對最多的類型也就是字符串,而我們每天面對的最多的場景也就是對文字的處理。
varchar類型:用于存儲可變長的字符串,比定長char類型節(jié)省空間(在通常情況下)。除非設(shè)置row_format=fixed,每一行是定長存儲。varchar額外需要1~2個字節(jié)存儲字符串的長度。當(dāng)列的最大長度< span>字節(jié),用1個字節(jié)存儲長度。否則采取2個字節(jié)。而且在Mysql5以后,varchar字段不會將末尾的空格剔除了。
char類型:char是定長類型,那么在存取過程中,會根據(jù)字符串長度老老實實分配足夠的空間。定長字符串類型不容易產(chǎn)生磁盤碎片,對于定長短列,char比varchar更有效。比如存儲MD5或者SHA1值。
Blob類型:
存儲二進(jìn)制類型的大字段數(shù)據(jù),沒有排序規(guī)則以及字符集。
類型成員有:tinyblob;blob;mediumblob;longblob。
一般情況下存儲圖片、文檔文件,用之。存儲引擎在blob很大時借助外部存儲(操作系統(tǒng)FS接口)進(jìn)行特殊處理。
Text類型-對應(yīng)于Oracle的clob:
存儲字符方式存儲大字段類型數(shù)據(jù),有排序規(guī)則和字符集。
類型成員有:tinytext;text;mediumtext;longtext。
一般情況下存儲文章,html頁面內(nèi)容。同理,在text很大時借助外部存儲,進(jìn)行特殊處理。
經(jīng)驗:
1)一般獲取blob或者text記錄的時候,將原始記錄值進(jìn)行截斷——substring(字段名,大小)函數(shù)。之后再轉(zhuǎn)換成為相應(yīng)的字符串。這樣可以使用到Mysql的內(nèi)存臨時表了,而避免了從磁盤上去取數(shù)據(jù)的IO。
2)臨時表的大小超過配置的max_ heap_table_size(tmp_table_size)的時候內(nèi)存臨時表將使用磁盤臨時表。(也就是說將內(nèi)存密集型的case負(fù)載到了IO密集型)
4. 枚舉類型
Mysql存取枚舉,緊湊。一般代替常用的字符串類型。Mysql將枚舉列表的個數(shù)將其壓縮位1~2個字節(jié)存儲。之后,再將每一個枚舉值保存為一個整數(shù)數(shù)字,將整數(shù)數(shù)字與枚舉字符串的值做鍵值對兒的映射。也就是說,實際上表中引用枚舉的字段值存儲的是數(shù)字。
實驗證明,著實如此。
CREATE TABLE user2 (
id int(10) unsigned NOT NULL AUTO_INCREMENT,
type enum(‘魏’,’蜀’,’吳’) CHARACTER SET utf8 DEFAULT ‘魏’,
PRIMARY KEY (id)
) ENGINE=InnoDB
執(zhí)行查詢的時候?qū)ype字段都加上一個數(shù)字,得出來的結(jié)果居然是數(shù)字,證明枚舉底層使用的是數(shù)值類型進(jìn)行的存取枚舉。而且若是非要枚舉做外鍵,那么基于基準(zhǔn)測試給出的結(jié)果,枚舉與枚舉之間的外鍵關(guān)聯(lián)QPS是最高的。Mysql內(nèi)部對枚舉的數(shù)值做了相應(yīng)的排序優(yōu)化。
場景:能夠使用枚舉做常量時,盡量不要用字符串類型。
5. 日期和時間
日期和時間類型有以下幾種:date;time;year;timestamp;datetime;
date:相當(dāng)于截取了datetime的date,范圍時從公元0年1月1日,可以到公元9999年12月31日。
time:相當(dāng)于截取了datetime的time,范圍就是一天的24小時。
year:比較尷尬,臨界值是69和70,輸入69,基本上代表2069年。70就是代表1970年。范圍值是0~99,分別代表,0~69:2000~2069;70~99:1970~1999。不是特殊情況,基本棄用。
最常用的應(yīng)該是datetime與timestamp。
datetime:使用8個字節(jié)存儲日期與時間,那么可以得出結(jié)論,date使用4個字節(jié),time也是4個字節(jié)。精確到秒級別,與時區(qū)無關(guān)。范圍是從1000年到9999年的日期和時間。
timestamp:使用4個字節(jié)存儲日期與時間,不過范圍只能表示從1970年~2038年。如果沒有什么意外,看到這篇文章的同志們,大多數(shù)都能活到那一年,之后會不會出現(xiàn)timestamp2這種類型來擴(kuò)大時間戳的范圍,那就得看是不是有支持更大整型數(shù)值的類型出現(xiàn)了。在應(yīng)用層使用long類型插入該字段的值,最后可以存儲正確的日期時間,而且該字段依賴于時區(qū)。做國際化產(chǎn)品的時候需要特別注意!
6. SET類型
用于存儲集合類型的集合類,集合元素里面基本上存儲的是常量值,書中舉了一個比較貼切的列子,就是權(quán)限控制的權(quán)限集合。其實也是代表一個人的聚合元素。但是呢,其實權(quán)限控制完全用整形也可以表示,就是類似于linux的權(quán)限數(shù)字,比如777代表該文件夾無任何限制可以被其他用戶使用,訪問,修改。
對于SET類型(mysql數(shù)據(jù)庫中),在Java應(yīng)用層獲取該類型的值,使用字符串就可以,不過獲取的值還需要另外處理,拆解字符串為字符串?dāng)?shù)組(使用,進(jìn)行拆分)。
7. 特殊字段-ipv4地址的存取
存取ip地址可以使用mysql中的兩個函數(shù)將ipv4字符串轉(zhuǎn)換成為整數(shù),整數(shù)的存取比字符串快。兩個特殊的函數(shù)是:
Ip地址轉(zhuǎn)成數(shù)字:select inet_aton(“192.168.1.1”);
結(jié)果
+————————–+
| inet_aton(“192.168.1.1”) |
+————————–+
| 3232235777 |
+————————–+
數(shù)字轉(zhuǎn)換成為ip地址
select inet_ntoa(3232235778);
結(jié)果為:
+———————–+
| inet_ntoa(3232235778) |
+———————–+
| 192.168.1.2 |
+———————–+
總結(jié)
以上是生活随笔為你收集整理的MySQL类型介绍以及适用范围的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: MySQL数据库优化技巧
- 下一篇: 设计模式概览