学过数据库理论的读者,都应该还记得关于CHAR和VARCHAR的性能对比:CHAR比VARCHAR更快,因为CHAR是固定长度的,而VARCHAR需要增加一个长度标识,处理时需要多一次运算。
针对这种情况,我做了一下基准测试,基准测试环境如下:
【硬件配置】
硬件 |
配置 |
CPU |
Intel(R) Xeon(R) CPU E5620 主频2.40GHz, 物理CPU 2个,逻辑CPU 16个 |
内存 |
24G(6块 * 4G DDR3 1333 REG) |
硬盘 |
300G * 3个,SAS硬盘 15000转,无RAID,有RAID卡,且开了回写功能 |
OS |
RHEL5 |
MySQL |
5.1.49/5.1.54 |
【MySQL配置】
配置项 |
配置 |
innodb_buffer_pool_size |
18G |
innodb_log_file_size |
200M |
innodb_log_files_in_group |
3 |
sync_binlog |
100 |
innodb_flush_log_at_trx_commit |
2 |
【表配置】
VARCHAR平均长度200,CHAR长度250,其它配置如下:
配置项 |
配置 |
记录数 |
1000万,2000万,5000万,1亿 |
存储引擎 |
Innodb |
行格式 |
compact |
性能测试结果如下:
【更新】更新时VARCHAR也是随机长度
测试结果展现了一个与理论不太相符的现象:当表大小小于Innodb buffer pool时,CHAR和VARCHAR没有差别,而在表大小大于Innodb buffer pool时,VARCHAR性能反而更高!这是为什么呢?
首先,性能是综合硬件、配置、表记录数、业务模型等多种因素综合后的结果,单一因素的差异,对整体来说可能几乎没有影响;
例如,执行一个操作需要100ms,而CHAR 比 VARCHAR性能上只快了1微秒,那么最终的性能就不会有影响。
这就是当Innodb buffer pool足够大时,CHAR 和VARCHAR没有差别的原因。
再次,理论上CHAR比VARCHAR快的根本原因是站在CPU的角度来说的,但性能是综合各种因素后的最终结果,当Innodb buffer pool小于表大小时,"磁盘读写"成为了性能的关键因素,而VARCHAR更短,因此性能反而比CHAR高。
最后,有朋友可能会认为,VARCHAR更新时如果新的数据比旧的数据要长,可能需要移动数据,导致性能更低;从实测结果来看,这种操作对最终的性能也是没有明显影响的。应该是因为Innodb采用页管理数据,数据移动是先在内存里完成,再写到磁盘,因此数据即使移动也很快。
【应用技巧】
基于以上测试结果和分析,我个人认为一般情况下优先使用VARCHAR,特别是字符串的平均长度比最大长度要小很多的情况;
当然,如果你的字符串本来就很短,例如只有10个字符,那么就优先选CHAR了
转载自: http://tech.uc.cn/?p=1910
相关推荐
1.数据库三范式是什么? 2.有哪些数据库优化方面的经验?...9.mysql 中 varchar 与 char 的区别以及 varchar(50)中的 50 代表的涵 义? 10.MySQL 中 InnoDB 支持的四种事务隔离级别名称,以及逐级之间的区 别?
3、MySQL中varchar与char的区别以及varchar(50)中的50代表的涵义? 4、date,datetime和timestamp数据类型有什么区别? 5、union 与union all的区别? 6、简述Mysql几种Join的区别? 7、drop,delete与truncate的区别?...
本工程用于研究Spring、Ibatis结合MySQL数据库的使用方法 本工程编码方式:UTF-8 须执行的SQL语句: CREATE DATABASE `test`; USE `test`; DROP TABLE IF EXISTS `student`; CREATE TABLE `student` ( `id` char...
`city_code` char(6) NOT NULL DEFAULT '' COMMENT '区号', `name` varchar(50) NOT NULL DEFAULT '' COMMENT '名称', `short_name` varchar(50) NOT NULL DEFAULT '' COMMENT '简称', `merger_name` varchar(50...
本工程用于研究Ibatis和MySQL结合使用的方法 本工程编码方式:UTF-8 须执行的SQL语句: CREATE DATABASE `test`; USE `test`; DROP TABLE IF EXISTS `student`; CREATE TABLE `student` ( `id` char(36) NOT NULL...
1、MySQL的复制原理以及流程 基本原理流程,3个线程...3、MySQL中varchar与char的区别以及var50)中的50代表的涵义 (1)、varchar与char的区别 (2)、var50)中50的涵义 (3)、int(20)中20的涵义 (4)、mysql为什么这么设计
3 MySQL中varchar与char的区别以及varchar(50)中的50代表的涵义 2 3.1 varchar与char的区别 2 3.2 varchar(50)中50的涵义 2 3.3 int(20)中20的涵义 2 3.4 MySQL为什么这么设计? 2 4 问了InnoDB的事务与日志的实现...
3、MySQL中varchar与char的区别以及varchar(50)中的50代表的涵义 4、问了innodb的事务与日志的实现 5、MySQL binlog的几种日志录入格式以及区别 6、MySQL数据库cpu飙升到500%的话他怎么处理? 7、sql优化各种方法 8...
本工程以“银行账号转账”为例子演示了 如何处理Ibatis结合MySQL数据库使用时的事务操作 本工程编码方式:UTF-8 须执行的SQL语句: CREATE DATABASE `test`; USE `test`; CREATE TABLE `lm_bank_card` ( `id` ...
MYSQL 数据库服务器性能分析的方法命令有哪些?如何控制 HEAP 表的最大尺寸?MyISAM Static 和 MyISAM Dynamic 有什么区别?federated 表是什么?如果一个表有一列定义为 TIMESTAMP,将发生什么?
简述在 MySQL 数据库中 MyISAM 和 InnoDB 的区别 Mysql 中 InnoDB 支持的四种事务隔离级别名称,以及逐级之间的区 别? CHAR 和 VARCHAR 的区别? 主键和候选键有什么区别? myisamchk 是用来做什么的? MyISAM ...
CHAR和VARCHAR的区别? NOW()和CURRENT_DATE()有什么区别? 各种索引的概念:索引,主键,唯一索引,联合索引,索引分类 建立索引的使用场景 Myql中的事务回滚机制,持久性,隔离级别的实现 说一说drop、delete与...
1.索引概叙 MySQL 5.0 1.1 对相关列使用索引,提高select操作的佳途径; 1.2 每种存储引擎对每个表... 1.5 MyISAM支持全文本索引(FULLTEXT),只限于char,varchar,text列,对整个列进行,不支持部分索引(前
本工程以“银行账号转账”为例子演示了如何处理Spring、Ibatis结合MySQL数据库使用时的事务操作 本工程编码方式:UTF-8 须执行的SQL语句: CREATE DATABASE `test`; USE `test`; CREATE TABLE `lm_bank_card` ( `...
11.4.1. CHAR和VARCHAR类型 11.4.2. BINARY和VARBINARY类型 11.4.3. BLOB和TEXT类型 11.4.4. ENUM类型 11.4.5. SET类型 11.5. 列类型存储需求 11.6. 选择正确的列类型 11.7. 使用来自其他数据库引擎的列类型 12. ...
4. char 和 varchar 的区别? 5. varchar(10) 和 varchar(20) 的区别? 6. 谈谈你对索引的理解? 7. 索引的底层使用的是什么数据结构? 8. 谈谈你对 B+ 树的理解? 9. 为什么 InnoDB 存储引擎选用 B+ 树而不是 B 树...
1.2 ⾓⾊表 CREATE TABLE `sys_role` ( `id` varchar(36) NOT NULL, `name` varchar(128) NOT NULL, `available` char(1) DEFAULT NULL COMMENT '是否可⽤,1:可⽤,0不可⽤', PRIMARY KEY (`id`) ) ENGINE=InnoDB ...
11.4.1. CHAR和VARCHAR类型 11.4.2. BINARY和VARBINARY类型 11.4.3. BLOB和TEXT类型 11.4.4. ENUM类型 11.4.5. SET类型 11.5. 列类型存储需求 11.6. 选择正确的列类型 11.7. 使用来自其他数据库引擎的列类型 12. ...
`FirstChar` varchar(45) DEFAULT '' COMMENT '首拼', `lng` varchar(45) DEFAULT '' COMMENT '经度', `Lat` varchar(45) DEFAULT '' COMMENT '纬度', `Remark1` varchar(45) DEFAULT '' COMMENT '是否行政区', ...