前言
MySQL 中有很多字段类型,比如整数、文本、浮点数,等等。如果类型定义合理,就能节省存储空间,提升数据查询和处理的速度;如果数据类型定义不合理,就有可能会导致数据超出取值范围,引发系统报错,甚至可能会出现计算错误的情况,进而影响到整个系统。
准确地定义字段类型,不但关系到数据存储的效率,而且会影响整个信息系统的可靠性。所以,我们必须要掌握不同字段的类型,包括它们的适用场景、定义方法
1、整数类型
在评估用哪种整数类型的时候,你需要考虑存储空间和可靠性的平衡问题:
- 用占用字节数少的整数类型可以节省存储空间;
- 要是为了节省存储空间,使用的整数类型取值范围太小,一旦遇到超出取值范围的情况,就可能引起系统错误,影响可靠性。
在实际工作中,系统故障产生的成本远远超过增加几个字段存储空间所产生的成本。因此,我建议你首先确保数据不会超过取值范围前提下,再去考虑如何节省存储空间。
2、浮点数类型
浮点数类型有个缺陷,就是不精准。因此,在一些对精确度要求较高的项目中,千万不要使用浮点数,不然会导致结果错误,甚至是造成不可挽回的损失。下面我来重点解释一下为什么 MySQL 的浮点数不够精准:
在一些对精度要求不高的场景下,比起占用同样的字节长度的定点数,浮点数表达的数值范围可以更大一些。
浮点类型取值范围大,但是不精准,适用于需要取值范围大,又可以容忍微小误差的科学计算场景(比如计算化学、分子建模、流体动力学等)
3、定点数类型
就像浮点数类型的存储方式,决定了它不可能精准一样,DECIMAL 的存储方式决定了它一定是精准的。
DECIMAL 是把十进制数的整数部分和小数部分拆开,分别转换成十六进制数进行存储。这样,所有的数值都可以精准表达了,不会存在因为无法表达而损失精度的问题。
定点数类型取值范围相对小,但是精准,没有误差,适合于对精度要求极高的场景(比如涉及金额计算的场景)
4、文本类型
TEXT 类型是 MySQL 支持的文本类型的一种。此外,MySQL 还支持 CHAR、VARCHAR、ENUM 和 SET 等文本类型。
因为不需要预先知道字符串的长度,系统会按照实际的数据长度进行存储,所以 TEXT 类型最为灵活方便
不过,需要注意的是,TEXT 也有一个问题:由于实际存储的长度不确定,MySQL 不允许 TEXT 类型的字段做主键。遇到这种情况,你只能采用 CHAR(M),或者 VARCHAR(M)
所以,建议在项目中,只要不是主键字段,就可以按照数据可能的最大长度,选择这几种 TEXT 类型中的的一种,作为存储字符串的数据类型。
5、日期时间类型
用得最多的日期时间类型,就是 DATETIME。
虽然 MySQL 也支持 YEAR(年)、TIME(时间)、DATE(日期),以及 TIMESTAMP 类型,但是我建议你,在实际项目中,尽量用 DATETIME 类型。因为这个数据类型包括了完整的日期和时间信息,使用起来比较方便。
如果日期时间信息分散在好几个字段,就会很不容易记,而且查询的时候,SQL 语句也会更加复杂。
为了确保数据的完整性和系统的稳定性,优先考虑使用 DATETIME 类型。因为虽然 DATETIME 类型占用的存储空间最多,但是它表达的时间最为完整,取值范围也最大。
为什么时间类型 TIME 的取值范围不是 -23:59:59~23:59:59 呢?
原因是 MySQL 设计的 TIME 类型,不光表示一天之内的时间,而且可以用来表示一个时间间隔,这个时间间隔可以超过 24 小时。
总结
今天,我给你介绍了几个常用的字段数据类型,包括整数类型、浮点数类型、定点数类型、文本类型和日期时间类型。同时,我们还清楚了为什么整数类型用得少,浮点数为什么不精准,以及常用的日期时间类型。
最后,分享 1 个小技巧:
在定义数据类型时,如果确定是整数,就用 INT;
如果是小数,一定用定点数类型 DECIMAL;
如果是字符串,只要不是主键,就用TEXT;
如果是日期与时间,就用 DATETIME。
这样做的好处是,首先确保你的系统不会因为数据类型定义出错。
不过,凡事都是有两面的,可靠性好,并不意味着高效。比如,TEXT 虽然使用方便,但是效率不如 CHAR(M) 和 VARCHAR(M)。