一、字符串类型
在SQL中,将字符串类型分成了6类:char,varchar,text,blob,enum和set。
1.1 定长字符串
定义:char,磁盘(二维表)在定义结构的时候,就以及确定了最终数据的存储长度。
Char(L): L代表length,可以存储的长度,单位为字符,最大长度值可以为255.
Char(4):在UTF8环境下,需要4*3=12个字节。
1.2 变长字符串
定义:varchar,在分配空间的时候,按照最大的空间分配,但是实际上最终用了多少,是根据具体的数据来确定。
Varchar(L): L表示字符长度,理论长度是65536个字符,但是会多出1到2个字节来确定存储的实际长度
Varchar(10): 的确存了10个汉字,UTF8环境,10*3+1=31
存储了3个汉字,UTF8环境,3*3+1=10(bytes)
定长与变长的存储实际空间(UTF8)
存储实际空间
Char(4)
Varchar(4)
Char占用字节
Varchar占用字节
ABCD
ABCD
ABCD
4*3=12
4*3+1=13
A
A
A
4*3=12
1*3+1=4
ABCDE
×
×
数据超过长度
数据超过长度
如何选择定长或者是变长字符串呢?
定长的磁盘空间比较浪费,但是效率高:如果数据基本上确定长度都一样,就是使用定长,如:身份证,电话号码,手机号码等
变长的磁盘空间比较节省,但是效率低:如果数据不能确定长度(不同数据有变化),如姓名、地址等。
1.3 文本字符串
如果数据量非常大,通常说超过255个字符就会使用文本字符串
文本字符串根据存储的格式进行分类:text和blob
Text: 存储文字(二进制数据实际上都是存储路径)
Blob: 存储二进制数据(通常不用)
1.4 枚举字符串
枚举定义:enum,事先将所有可能出现的结果都设计好,实际上存储的数据都必须是规定好的数据中的一个。
枚举的使用方式
定义:enum(可能出现的元素列表); //如 enum(‘男’,‘女’,‘不男不女’,‘妖’,‘保密’);
使用:存储数据,只能存储上面定义好的数据
(a) 创建枚举表
1 CREATE TABLE my_enum(gender enum('男','女','保密')) charset utf8;
(b)加入数据 作用之一:规范数据格式;数据只能是规定的数据的其中一个
1 insert into my_enum values('男'),('保密'); --有效数据
2 insert into my_enum values('male'); --错误数据(没有male元素)
(b)作用之二:节省存储空间(枚举通常有一个别名:单选框):枚举实际存储的是数值而不是字符串本身。
在MYSQL中,系统也是字段转换成数据格式的:而且基本与PHP一样(尤其是字符串转数字)
证明字段存储的数据是数值:将数据取出来+0 就可以判断出原来的数据存的到底是字符串还是数值:如果是字符串最终结果永远为0,否则就是其他值。
(c) 将字段结果取出来进行+0运算
1 select gender+0,gender from my_enum;
找出来枚举元素的实际规律:按照元素出现的顺序,从1开始编号
enum
1,2, ~枚举选项量(65535)
内部存储是整型表示。字段值只能是某一个
枚举原理:枚举在进行数据规范的时候(定义的时候),系统会自动建立一个数字与枚举元素的对应关系(关系放到日志中):然后在进行数据插入的时候,系统自动将字符转换成对应的数字存储,然后在进行数据提取的时候,系统自动将数值转换成对应的字符串显示。
因为枚举实际存储的是数值,所以可以直接插入数值
(d)数值插入枚举元素
1 insert into my_enum values(1),(2);2 select gender+0,gender from my_enum;
1.5 集合字符串
集合跟枚举很类似:实际存储的是数值,而不是字符串(集合是多选)
集合使用方式
定义:Set(元素列表)
使用:可以使用元素列表中的元素(多个),使用逗号分隔
Set
1、2、3、4、8。元素数量:64
(a) 创建集合表
1 create table my_set(hobby set('篮球','足球','乒乓球','羽毛球','排球','台球','网球','棒球'))charset utf8;
0 1 0 0 0 1 1 0
集合中:每一个元素都是对应一个二进制位,被选中为1,没有则为0;最后反过来。
反过来: 01100010=98
(b) 插入数据:可以使用多个元素字符串组合,也可以直接插入数值
1 insert into my_set values('足球,台球,网球');2 insert into my_set values('3'); --代表乒乓球;3=1+2=篮球+足球
查看数据:数值+数据查看
(c)查看集合数据
1 select hobby +0,hobby from my_set; --- 预料之外的结果
98转成二进制=64+32+2=01100010
(d)集合中每一个元素都是对应一个对应二进制位
1 insert into my_set values(255); --255对应二进制为11111111
集合中元素的顺序没有关系;最终系统都会去匹配顺序
颠倒元素出现的顺序
insert into my_set values('网球,台球,足球');select * from my_set;
集合的强大在于能够规范和节省空间:PHP也可以规范数据,但是对于PHP来说效率优先,而且数据的维护可以用通过数字进行,增加PHP的维护成本;PHP根本没有办法判断数据在数据库的形式。