MySQL建表注意事项
1、存储空间方面
-
核心思想:在选择数据类型时,优先使用占用空间小的数据类型,以节省存储空间。例如,当能确定字符串长度上限时,选择合适长度的固定长度字符串类型(如
char),避免使用过大长度的类型。 -
IP 地址示例
-
使用
UNSIGNED INT存储 IPv4 地址:将 IPv4 地址转换为无符号整数存储,仅需 4 字节空间,且整数比较效率高,适合范围查询和排序操作。但不直观,需借助INET_ATON()和INET_NTOA()函数进行转换。 -
使用
varchar(15)存储 IPv4 地址:每个字符占一个字节,加上长度占一个字节,实际占用空间根据 IP 地址具体长度有所不同,在磁盘空间充足且需要在数据库直接查看 IP 地址时可选用。
-
-
建议
-
数据类型选择前评估:在设计表结构时,充分评估数据的实际范围和增长可能性,精确选择数据类型和长度。例如对于年龄字段,使用
TINYINT(范围 0 - 255)就足以存储人类年龄,而无需使用INT。 -
考虑查询性能与空间平衡:虽然小数据类型节省空间,但有时可能影响查询性能。如在频繁进行范围查询的字段上,选择合适的数据类型和索引策略更为重要。例如,对于经常进行时间范围查询的日期字段,使用
DATE或DATETIME类型并配合适当索引,而不是为节省空间选择不合理的存储方式。
-
2、数据长度方面
-
核心思想:能用定长的
char类型存储时,尽量不用可变长度的varchar类型。 -
原因:
char类型无论实际存储的数据长度如何,都会占用固定空间;varchar虽按实际数据长度占用空间,但会额外存储长度信息,在某些场景下可能增加复杂性。 -
建议
-
根据业务场景权衡:
char类型虽有固定长度优势,但如果数据长度变化较大,varchar可能更节省空间。例如存储用户地址,地址长度差异大,使用varchar更合适;而对于像性别字段(固定为 “男” 或 “女”),使用char(1)即可。 -
避免过度追求定长:在一些情况下,
varchar额外的长度前缀开销较小,若为追求定长而浪费过多空间并不划算。要综合考虑数据的平均长度、存储成本和查询性能等因素。
-
3、数据精度方面
-
核心思想:对于像金额这类对精度要求极高的字段,务必选择合适的数据类型以避免精度损失,MySQL 中一般使用
DECIMAL类型。 -
金额字段示例:金额字段使用不当可能导致严重后果,
DECIMAL类型可确保数据精度。 -
建议
-
合理设置 DECIMAL 精度:在使用
DECIMAL类型存储金额时,要根据业务需求合理设置精度和小数位数。例如,对于一般货币金额,DECIMAL(10, 2)表示总长度为 10 位,其中小数部分为 2 位,可满足常见金额范围。 -
避免中间计算精度损失:在涉及金额计算的业务逻辑中,不仅要注意存储时的精度,还要注意在程序计算过程中避免精度损失。例如在 Java 中使用
BigDecimal进行精确计算。
-
VARCHAR 存储结构及字节数计算
阐述VARCHAR类型的存储结构,包括字符数据部分和长度前缀部分。字符数据部分的字节数取决于字符编码,长度前缀部分根据VARCHAR最大长度不同而占用不同字节数(最大长度≤255 字节时,长度前缀占 1 字节;最大长度>255 字节时,长度前缀占 2 字节)。
对于一个字符串他所占的字节数,需要知道如何计算
VARCHAR 的存储结构 在 MySQL 中,VARCHAR 是一种可变长度的字符串数据类型,它由两部分组成: 字符数据:存储实际的字符串内容。 长度前缀:用于记录字符串的实际长度。 这种设计使得 VARCHAR 类型能够灵活地存储不同长度的字符串,同时节省存储空间。
字符数据部分 VARCHAR(15) 表示该字段可以存储最多 15 个字符。字符的实际占用字节数取决于字符编码。 (1) 单字节字符 如果使用的是单字节字符集(如 latin1 或 ascii),每个字符占用 1 个字节。例如: 存储字符串 "hello": 字符数据部分:5 个字符 × 1 字节/字符 = 5 字节。 (2) 多字节字符 如果使用的是多字节字符集(如 utf8mb4),字符占用的字节数会根据字符的不同而变化: ASCII 字符(如 a、1、@ 等):1 字节。 非 ASCII 的拉丁字符(如 é、ö 等):2 字节。 中文、日文、韩文等常见 Unicode 字符:3 字节。 特殊的 Unicode 字符(如表情符号):4 字节。 例如: 存储字符串 "测试"(中文字符): 字符数据部分:2 个字符 × 3 字节/字符 = 6 字节。 存储字符串 "😊"(表情符号): 字符数据部分:1 个字符 × 4 字节/字符 = 4 字节。
长度前缀部分 VARCHAR 类型在存储时会额外记录字符串的实际长度,这部分称为长度前缀。 (1) 长度前缀的大小 长度前缀的大小取决于 VARCHAR 的最大长度: 如果最大长度小于或等于 255 字节,长度前缀占用 1 字节。 如果最大长度大于 255 字节(例如 VARCHAR(256) 或更大),长度前缀占用 2 字节。 对于 VARCHAR(15): 最大长度为 15 字节(假设全部是单字节字符),因此长度前缀占用 1 字节。
总字节数的计算 VARCHAR(15) 的总字节数由字符数据部分和长度前缀部分组成。 (1) 单字节字符示例 假设存储的字符串为 "hello"(5 个 ASCII 字符): 字符数据部分:5 个字符 × 1 字节/字符 = 5 字节。 长度前缀部分:1 字节。 总字节数:5 字节 + 1 字节 = 6 字节。 (2) 多字节字符示例 假设存储的字符串为 "测试"(2 个中文字符): 字符数据部分:2 个字符 × 3 字节/字符 = 6 字节。 长度前缀部分:1 字节。 总字节数:6 字节 + 1 字节 = 7 字节。
最大字节数 对于 VARCHAR(15),最大字节数的计算如下: 最大字符数据部分: 如果全部是单字节字符:15 字节。 如果全部是 4 字节字符(如表情符号):15 × 4 = 60 字节。 长度前缀部分:1 字节。 最大总字节数: 如果全部是单字节字符:15 字节 + 1 字节 = 16 字节。 如果全部是 4 字节字符:60 字节 + 1 字节 = 61 字节。
特殊情况 (1) 空字符串 如果存储的是空字符串(''): 字符数据部分:0 字节。 长度前缀部分:1 字节(记录长度为 0)。 总字节数:0 字节 + 1 字节 = 1 字节。 (2) 不同字符集的混合 如果字符串中包含多种类型的字符(例如,既有 ASCII 字符,又有中文字符),字符数据部分的字节数会根据每个字符的实际编码长度计算。例如: 存储字符串 "hello测试": 字符数据部分:5 个 ASCII 字符 × 1 字节/字符 + 2 个中文字符 × 3 字节/字符 = 5 字节 + 6 字节 = 11 字节。 长度前缀部分:1 字节。 总字节数:11 字节 + 1 字节 = 12 字节。
总结 VARCHAR(15) 的实际占用字节数取决于存储的字符串内容和字符编码。 最小字节数:1 字节(空字符串)。 最大字节数: 如果全部是单字节字符:16 字节。 如果全部是 4 字节字符:61 字节。 长度前缀:始终占用 1 字节(因为 VARCHAR(15) 的最大长度小于 255 字节)。 通过这种方式,VARCHAR 类型能够灵活地存储不同长度的字符串,同时节省存储空间。
二、其他注意事项
1. 主键选择
-
唯一性与稳定性:主键应具有唯一性,且在数据生命周期内保持不变。例如,对于用户表,使用自增 ID 作为主键较为合适,因为它能保证唯一性且不会随用户信息变更而改变。避免使用业务字段作为主键,除非该业务字段绝对不会发生变化(如身份证号用于用户表时,虽具有唯一性,但存在号码变更的可能性,一般不作为主键)。
-
数据类型选择:尽量选择简单、占用空间小的数据类型作为主键,如
INT或BIGINT。这不仅节省存储空间,还能提高索引效率和查询性能。
2. 索引设计
-
合理创建索引:在经常用于查询条件、排序或连接操作的字段上创建索引。例如,在订单表的
order_date字段上创建索引,可加速按日期查询订单的操作。但索引并非越多越好,过多索引会增加存储开销和数据修改的成本(每次数据修改都可能需要更新相关索引)。 -
联合索引:当多个字段经常一起用于查询条件时,可创建联合索引。注意联合索引的字段顺序,一般将选择性高(即不同值较多)的字段放在前面,以提高索引效率。例如,在订单表中,如果经常根据
member_id和order_status查询订单,可创建联合索引(member_id, order_status)。
3. 表关系设计
-
规范化与反规范化:遵循数据库规范化原则设计表关系,减少数据冗余,保证数据一致性。但在某些性能敏感的场景下,可适当进行反规范化,通过增加少量冗余数据来提高查询性能。例如,在订单表中存储会员的部分基本信息(如会员姓名),可减少查询订单时与会员表的连接操作,但要注意数据更新时保持冗余数据的一致性。
-
外键约束:合理使用外键约束来维护表之间的参照完整性。例如,在订单表中设置
member_id作为外键关联会员表的member_id,确保订单表中的会员 ID 在会员表中存在,防止无效数据插入。但外键约束会增加数据插入、更新和删除的开销,在性能要求极高的场景下需谨慎使用。
4. 字符集与排序规则
-
字符集选择:根据应用程序处理的数据类型和地域需求选择合适的字符集。如应用主要处理英文和数字,
latin1或ascii字符集即可;若涉及多种语言,特别是中文、日文、韩文等,utf8mb4字符集是较好选择,它能支持更广泛的字符范围。 -
排序规则:排序规则决定了字符的比较和排序方式。不同的排序规则可能会影响查询结果和性能。例如,
utf8mb4_general_ci是常用的不区分大小写的排序规则,而utf8mb4_bin是区分大小写的排序规则,应根据业务需求选择合适的排序规则。
1490

被折叠的 条评论
为什么被折叠?



