测试缘由
一个开发同事做了一个框架,里面主键是uuid,我跟他建议说mysql不要用uuid用自增主键,自增主键效率高,他说不一定高,我说innodb的索引特性导致了自增id做主键是效率最好的,为了拿实际的案例来说服他,所以准备做一个详细的测试。
作为互联网公司,一定有用户表,而且用户表uc_user基本会有百万记录,所以在这个表基础上准测试数据来进行测试。
测试过程是目前我想到的多方位的常用的几种类型的sql进行测试,当然可能不太完善,欢迎大家留言提出更加完善的测试方案或者测试sql语句。
1、准备表以及数据uc_user,自增id为主键,表结构类似如下:
create table `uc_user` (
`id` bigint(20) not null auto_increment comment '主键',
`user_name` varchar(100) default null comment '用户名',
`user_pwd` varchar(200) default null comment '密码',
`birthday` datetime default null comment '生日',
`name` varchar(200) default null comment '姓名',
`user_icon` varchar(500) default null comment '头像图片',
`sex` char(1) default null comment '性别, 1:男,2:女,3:保密',
`nickname` varchar(200) default null comment '昵称',
`stat` varchar(10) default null comment '用户状态,01:正常,02:冻结',
`user_mall` bigint(20) default null comment '当前所属mall',
`last_login_date` datetime default null comment '最后登录时间',
`last_login_ip` varchar(100) default null comment '最后登录ip',
`src_open_user_id` bigint(20) default null comment '来源的联合登录',
`email` varchar(200) default null comment '邮箱',
`mobile` varchar(50) default null comment '手机',
`is_del` char(1) default '0' comment '是否删除',
`is_email_confirmed` char(1) default '0' comment '是否绑定邮箱',
`is_phone_confirmed` char(1) default '0' comment '是否绑定手机',
`creater` bigint(20) default null comment '创建人',
`create_date` datetime default current_timestamp comment '注册时间',
`update_date` datetime default current_timestamp comment '修改日期',
`pwd_intensity` char(1) default null comment '密码强度',
`mobile_tgc` char(64) default null comment '手机登录标识',
`mac` char(64) default null comment 'mac地址',
`source` char(1) default '0' comment '1:web,2:ios,3:android,4:wifi,5:管理系统, 0:未知',
`activate` char(1) default '1' comment '激活,1:激活,0:未激活',
`activate_type` char(1) default '0' comment '激活类型,0:自动,1:手动',
primary key (`id`),
unique key `user_name` (`user_name`),
key `mobile` (`mobile`),
key `idx_mobile_tgc` (`mobile_tgc`,`id`),
key `idx_email` (`email`,`id`),
key `idx_create_date` (`create_date`,`id`),
key `idx_update_date` (`update_date`)
) engine=innodb auto_increment=7122681 default charset=utf8 comment='用户表'
uc_user_pk_varchar表,字符串id为主键,采用uuid
create table `uc_user_pk_varchar_1` (
`id` varchar(36) character set utf8mb4 not null default '0' comment '主键',
`user_name` varchar(100) default null comment '用户名',
`user_pwd` varchar(200) default null comment '密码',
`birthday` datetime default null comment '生日',
`name` varchar(200) default null comment '姓名',
`user_icon` varchar(500) default null comment '头像图片',
`sex` char(1) default null comment '性别, 1:男,2:女,3:保密',
`nickname` varchar(200) default null comment '昵称',
`stat` varchar(10) default null comment '用户状态,01:正常,02:冻结',
`user_mall` bigint(20) default null comment '当前所属mall',
`last_login_date` datetime default null comment '最后登录时间',
`last_login_ip` varchar(100) default null comment '最后登录ip',
`src_open_user_id` bigint(20) default null comment '来源的联合登录',
`email` varchar(200) default null comment '邮箱',
`mobile` varchar(50) default null comment '手机',
`is_del` char(1) default '0' comment '是否删除',
`is_email_confirmed` char(1) default '0' comment '是否绑定邮箱',
`is_phone_confirmed` char(1) default '0' comment '是否绑定手机',
`creater` bigint(20) default null comment '创建人',
`create_date` datetime default current_timestamp comment '注册时间',
`update_date` datetime default current_timestamp comment '修改日期',
`pwd_intensity` char(1) default null comment '密码强度',
`mobile_tgc` char(64) default null comment '手机登录标识',
`mac` char(64) default null comment 'mac地址',
`source` char(1) default '0' comment '1:web,2:ios,3:android,4:wifi,5:管理系统, 0:未知',
`activate` char(1) default '1' comment '激活,1:激活,0:未激活',
`activate_type` char(1) default '0' comment '激活类型,0:自动,1:手动',
primary key (`id`),
unique key `user_name` (`user_name`),
key `mobile` (`mobile`),
key `idx_mobile_tgc` (`mobile_tgc`,`id`),
key `idx_email` (`email`,`id`),
key `idx_create_date` (`create_date`,`id`),
key `idx_update_date` (`update_date`)
) engine=innodb default charset=utf8 comment='用户表';
2、500w数据测试2.1 录入500w数据,自增id节省一半磁盘空间确定两个表数据量
# 自增id为主键的表
mysql> select count(1) from uc_user;
+----------+
| count(1) |
+----------+
| 5720112 |
+----------+
1 row in set (0.00 sec)
mysql>
# uuid为主键的表
mysql> select count(1) from uc_user_pk_varchar_1;
+----------+
| count(1) |
+----------+
| 5720112 |
+----------+
1 row in set (1.91 sec)
占据的空间容量来看,自增id比uuid小一半左右。
主键类型
数据文件大小
占据容量
自增id
-rw-rw---- 1 mysql mysql 2.5g aug 11 18:29 uc_user.ibd
2.5 g
uuid
-rw-rw---- 1 mysql mysql 5.4g aug 15 15:11 uc_user_pk_varchar_1.ibd
5.4 g
2.2 单个数据走索引查询,自增id和uuid相差不大主键类型
sql语句
执行时间 (秒)
自增id
select sql_no_cache t.* from test.`uc_user` t where t.`mobile` ='14782121512';
0.118
uuid
select sql_no_cache t.* from test.`uc_user_pk_varchar_1` t where t.`mobile` ='14782121512';
0.117
自增id
select sql_no_cache t.* from test.`uc_user` t where t.`mobile` in( '14782121512','13761460105');
0.049
uuid
select sql_no_cache t.* from test.`uc_user_pk_varchar_1` t where t.`mobile` in('14782121512','13761460105');
0.040
自增id
select sql_no_cache t.* from test.`uc_user` t where t.`create_date`='2013-11-24 10:26:36' ;
0.139
uuid
select sql_no_cache t.* from test.`uc_user_pk_varchar_1` t where t.`create_date`='2013-11-24 10:26:43' ;
0.126
2.3 范围like查询,自增id性能优于uuid主键类型
sql语句
执行时间 (秒)
(1)模糊范围查询1000条数据,自增id性能要好于uuid
自增id
select sql_no_cache t.* from test.`uc_user` t where t.`mobile` like '147%' limit 1000;
1.784
uuid
select sql_no_cache t.* from test.`uc_user_pk_varchar_1` t where t.`mobile` like '147%' limit 1000;
3.196
(2)日期范围查询20条数据,自增id稍微弱于uuid
自增id
select sql_no_cache t.* from test.`uc_user` t where t.`create_date` > '2016-08-01 10:26:36' order by t.`update_date` desc limit 20;
0.601
uuid
select sql_no_cache t.* from test.`uc_user_pk_varchar_1` t where t.`create_date` > '2016-08-01 10:26:36' order by t.`update_date` desc limit 20;
0.543
(3)范围查询200条数据,自增id性能要好于uuid
自增id
select sql_no_cache t.* from test.`uc_user` t where t.`create_date` > '2016-07-01 10:26:36' order by t.`update_date` desc limit 200;
2.314
uuid
select sql_no_cache t.* from test.`uc_user_pk_varchar_1` t where t.`create_date` > '2016-07-01 10:26:36' order by t.`update_date` desc limit 200;
3.229
范围查询总数量,自增id要好于uuid
自增id
select sql_no_cache count(1) from test.`uc_user` t where t.`create_date` > '2016-07-01 10:26:36' ;
0.514
uuid
select sql_no_cache count(1) from test.`uc_user_pk_varchar_1` t where t.`create_date` > '2016-07-01 10:26:36' ;
1.092
ps:在有缓存的情况下,两者执行效率没有相差很小。
2.4 写入测试,自增id是uuid的4倍主键类型
sql语句
执行时间 (秒)
自增id
update test.`uc_user` t set t.`mobile_tgc`='t2' where t.`create_date` > '2016-05-03 10:26:36' and t.`create_date` <'2016-05-04 00:00:00' ;
1.419
uuid
update test.`uc_user_pk_varchar_1` t set t.`mobile_tgc`='t2' where t.`create_date` > '2016-05-03 10:26:36' and t.`create_date` <'2016-05-04 00:00:00' ;
5.639
自增id
insert into test.`uc_user`( id, `user_name`, `user_pwd`, `birthday`, `name`, `user_icon`, `sex`, `nickname`, `stat`, `user_mall`, `last_login_date`, `last_login_ip`, `src_open_user_id`, `email`, `mobile`, `is_del`, `is_email_confirmed`, `is_phone_confirmed`, `creater`, `create_date`, `update_date`, `pwd_intensity`, `mobile_tgc`, `mac`, `source`, `activate`, `activate_type` ) select null, concat('110',`user_name`,8), `user_pwd`, `birthday`, `name`, `user_icon`, `sex`, `nickname`, `stat`, `user_mall`, `last_login_date`, `last_login_ip`, `src_open_user_id`, `email`, concat('110',trim(`mobile`)), `is_del`, `is_email_confirmed`, `is_phone_confirmed`, `creater`, `create_date`, `update_date`, `pwd_intensity`, `mobile_tgc`, `mac`, `source`, `activate`, `activate_type` from `test`.`uc_user_1` limit 100;
0.105
uuid
insert into test.`uc_user_pk_varchar_1`( id, `user_name`, `user_pwd`, `birthday`, `name`, `user_icon`, `sex`, `nickname`, `stat`, `user_mall`, `last_login_date`, `last_login_ip`, `src_open_user_id`, `email`, `mobile`, `is_del`, `is_email_confirmed`, `is_phone_confirmed`, `creater`, `create_date`, `update_date`, `pwd_intensity`, `mobile_tgc`, `mac`, `source`, `activate`, `activate_type` ) select uuid(), concat('110',`user_name`,8), `user_pwd`, `birthday`, `name`, `user_icon`, `sex`, `nickname`, `stat`, `user_mall`, `last_login_date`, `last_login_ip`, `src_open_user_id`, `email`, concat('110',trim(`mobile`)), `is_del`, `is_email_confirmed`, `is_phone_confirmed`, `creater`, `create_date`, `update_date`, `pwd_intensity`, `mobile_tgc`, `mac`, `source`, `activate`, `activate_type` from `test`.`uc_user_1` limit 100;
0.424
2.5、备份和恢复,自增id性能优于uuid主键类型
sql语句
执行时间 (秒)
mysqldump备份
自增id
time mysqldump -utim -ptimgood -h192.168.121.63 test uc_user_500> uc_user_500.sql
28.59秒
uuid
time mysqldump -utim -ptimgood -h192.168.121.63 test uc_user_pk_varchar_500> uc_user_pk_varchar_500.sql
31.08秒
mysql恢复
自增id
time mysql -utim -ptimgood -h192.168.121.63 test < uc_user_500.sql
7m36.601s
uuid
time mysql -utim -ptimgood -h192.168.121.63 test < uc_user_pk_varchar_500.sql
9m42.472s
3、500w总结在500w记录表的测试下:
(1) 普通单条或者20条左右的记录检索,uuid为主键的相差不大几乎效率相同;
(2) 但是范围查询特别是上百成千条的记录查询,自增id的效率要大于uuid;
(3) 在范围查询做统计汇总的时候,自增id的效率要大于uuid;
(4) 在存储上面,自增id所占的存储空间是uuid的1/2;
(5) 在备份恢复上,自增id主键稍微优于uuid。
4、1000w数据测试4.1 录入1000w数据记录,看存储空间# 自增id为主键的表
mysql> use test;
database changed
mysql> select count(1) from uc_user_1;
+----------+
| count(1) |
+----------+
| 10698102 |
+----------+
1 row in set (27.42 sec)
# uuid为主键的表
mysql> select count(1) from uc_user_pk_varchar_1;
+----------+
| count(1) |
+----------+
| 10698102 |
+----------+
1 row in set (0.00 sec)
mysql>
占据的空间容量来看,自增id比uuid小一半左右:
主键类型
数据文件大小
占据容量
自增id
-rw-rw---- 1 mysql mysql 4.2g aug 20 23:08 uc_user_1.ibd
4.2 g
uuid
-rw-rw---- 1 mysql mysql 8.8g aug 20 18:20 uc_user_pk_varchar_1.ibd
8.8 g
4.2 单个数据走索引查询,自增id和 uuid效率比是:(2~3):1主键类型
sql语句
执行时间 (秒)
单条记录查询
自增id
select sql_no_cache t.* from test.`uc_user_1` t where t.`mobile` ='14782121512';
0.069
uuid
select sql_no_cache t.* from test.`uc_user_pk_varchar_1` t where t.`mobile` ='14782121512';
0.274
小范围查询
自增id
select sql_no_cache t.* from test.`uc_user_1` t where t.`mobile` in( '14782121512','13761460105');
0.050
uuid
select sql_no_cache t.* from test.`uc_user_pk_varchar_1` t where t.`mobile` in('14782121512','13761460105');
0.151
根据日期查询
自增id
select sql_no_cache t.* from test.`uc_user_1` t where t.`create_date`='2013-11-24 10:26:36' ;
0.269
uuid
select sql_no_cache t.* from test.`uc_user_pk_varchar_1` t where t.`create_date`='2013-11-24 10:26:43' ;
0.810
4.3 范围like查询,自增id性能优于uuid,比值(1.5~2):1主键类型
sql语句
执行时间 (秒)
(1)模糊范围查询1000条数据,自增id性能要好于uuid
自增id
select sql_no_cache t.* from test.`uc_user` t where t.`mobile` like '147%' limit 1000;
2.398
uuid
select sql_no_cache t.* from test.`uc_user_pk_varchar_1` t where t.`mobile` like '147%' limit 1000;
5.872
(2)日期范围查询20条数据,自增id稍微弱于uuid
自增id
select sql_no_cache t.* from test.`uc_user_1` t where t.`create_date` > '2016-08-01 10:26:36' order by t.`update_date` desc limit 20;
0.765
uuid
select sql_no_cache t.* from test.`uc_user_pk_varchar_1` t where t.`create_date` > '2016-08-01 10:26:36' order by t.`update_date` desc limit 20;
1.090
(3)范围查询200条数据,自增id性能要好于uuid
自增id
select sql_no_cache t.* from test.`uc_user_1` t where t.`create_date` > '2016-07-01 10:26:36' order by t.`update_date` desc limit 200;
1.569
uuid
select sql_no_cache t.* from test.`uc_user_pk_varchar_1` t where t.`create_date` > '2016-07-01 10:26:36' order by t.`update_date` desc limit 200;
2.597
范围查询总数量,自增id要好于uuid
自增id
select sql_no_cache count(1) from test.`uc_user_1` t where t.`create_date` > '2016-07-01 10:26:36' ;
1.129
uuid
select sql_no_cache count(1) from test.`uc_user_pk_varchar_1` t where t.`create_date` > '2016-07-01 10:26:36' ;
2.302
4.4 写入测试,自增id比uuid效率高,比值(3~10):1 主键类型
sql语句
执行时间 (秒)
修改一天的记录
自增id
update test.`uc_user_1` t set t.`mobile_tgc`='t2' where t.`create_date` > '2016-05-03 10:26:36' and t.`create_date` <'2016-05-04 00:00:00' ;
2.685
uuid
update test.`uc_user_pk_varchar_1` t set t.`mobile_tgc`='t2' where t.`create_date` > '2016-05-03 10:26:36' and t.`create_date` <'2016-05-04 00:00:00' ;
26.521
录入数据
自增id
insert into test.`uc_user_1`( id, `user_name`, `user_pwd`, `birthday`, `name`, `user_icon`, `sex`, `nickname`, `stat`, `user_mall`, `last_login_date`, `last_login_ip`, `src_open_user_id`, `email`, `mobile`, `is_del`, `is_email_confirmed`, `is_phone_confirmed`, `creater`, `create_date`, `update_date`, `pwd_intensity`, `mobile_tgc`, `mac`, `source`, `activate`, `activate_type` ) select null, concat('110',`user_name`,8), `user_pwd`, `birthday`, `name`, `user_icon`, `sex`, `nickname`, `stat`, `user_mall`, `last_login_date`, `last_login_ip`, `src_open_user_id`, `email`, concat('110',trim(`mobile`)), `is_del`, `is_email_confirmed`, `is_phone_confirmed`, `creater`, `create_date`, `update_date`, `pwd_intensity`, `mobile_tgc`, `mac`, `source`, `activate`, `activate_type` from `test`.`uc_user_1` limit 100;
0.534
uuid
insert into test.`uc_user_pk_varchar_1`( id, `user_name`, `user_pwd`, `birthday`, `name`, `user_icon`, `sex`, `nickname`, `stat`, `user_mall`, `last_login_date`, `last_login_ip`, `src_open_user_id`, `email`, `mobile`, `is_del`, `is_email_confirmed`, `is_phone_confirmed`, `creater`, `create_date`, `update_date`, `pwd_intensity`, `mobile_tgc`, `mac`, `source`, `activate`, `activate_type` ) select uuid(), concat('110',`user_name`,8), `user_pwd`, `birthday`, `name`, `user_icon`, `sex`, `nickname`, `stat`, `user_mall`, `last_login_date`, `last_login_ip`, `src_open_user_id`, `email`, concat('110',trim(`mobile`)), `is_del`, `is_email_confirmed`, `is_phone_confirmed`, `creater`, `create_date`, `update_date`, `pwd_intensity`, `mobile_tgc`, `mac`, `source`, `activate`, `activate_type` from `test`.`uc_user_1` limit 100;
1.716
4.5、备份和恢复,自增id性能优于uuid主键类型
sql语句
执行时间 (秒)
mysqldump备份
自增id
time mysqldump -utim -ptimgood -h192.168.121.63 test uc_user_1> uc_user_1.sql
0m50.548s
uuid
time mysqldump -utim -ptimgood -h192.168.121.63 test uc_user_pk_varchar_1> uc_user_pk_varchar_1.sql
0m58.590s
mysql恢复
自增id
time mysql -utim -ptimgood -h192.168.121.63 test < uc_user_1.sql
17m30.822s
uuid
time mysql -utim -ptimgood -h192.168.121.63 test < uc_user_pk_varchar_1.sql
23m6.360s
5、1000w总结在1000w记录表的测试下:
(1)普通单条或者20条左右的记录检索,自增主键效率是uuid主键的2到3倍;
(2)但是范围查询特别是上百成千条的记录查询,自增id的效率要大于uuid;
(3)在范围查询做统计汇总的时候,自增id主键的效率是uuid主键1.5到2倍;
(4)在存储上面,自增id所占的存储空间是uuid的1/2;
(5)在写入上面,自增id主键的效率是uuid主键的3到10倍,相差比较明显,特别是update小范围之内的数据上面。
(6)在备份恢复上,自增id主键稍微优于uuid。
6、mysql分布式架构的取舍分布式架构,意味着需要多个实例中保持一个表的主键的唯一性。这个时候普通的单表自增id主键就不太合适,因为多个mysql实例上会遇到主键全局唯一性问题。
6.1、自增id主键+步长,适合中等规模的分布式场景
在每个集群节点组的master上面,设置(auto_increment_increment),让目前每个集群的起始点错开 1,步长选择大于将来基本不可能达到的切分集群数,达到将 id 相对分段的效果来满足全局唯一的效果。
优点是:实现简单,后期维护简单,对应用透明。
缺点是:第一次设置相对较为复杂,因为要针对未来业务的发展而计算好足够的步长;
规划:
比如计划总共n个节点组,那么第i个节点组的my.cnf的配置为:
auto_increment_offset i
auto_increment_increment n
假如规划48个节点组,n为48,现在配置第8个节点组,这个i为8,第8个节点组的my.cnf里面的配置为:
auto_increment_offset 8
auto_increment_increment 48
6.2、uuid,适合小规模的分布式环境 对于innodb这种聚集主键类型的引擎来说,数据会按照主键进行排序,由于uuid的无序性,innodb会产生巨大的io压力,而且由于索引和数据存储在一起,字符串做主键会造成存储空间增大一倍。
在存储和检索的时候,innodb会对主键进行物理排序,这对auto_increment_int是个好消息,因为后一次插入的主键位置总是在最后。但是对uuid来说,这却是个坏消息,因为uuid是杂乱无章的,每次插入的主键位置是不确定的,可能在开头,也可能在中间,在进行主键物理排序的时候,势必会造成大量的 io操作影响效率,在数据量不停增长的时候,特别是数据量上了千万记录的时候,读写性能下降的非常厉害。
优点:搭建比较简单,不需要为主键唯一性的处理。
缺点:占用两倍的存储空间(在云上光存储一块就要多花2倍的钱),后期读写性能下降厉害。
6.3、雪花算法自造全局自增id,适合大数据环境的分布式场景由twitter公布的开源的分布式id算法snowflake(java版本)
idworker.java:
package com.demo.elk;
import org.slf4j.logger;
import org.slf4j.loggerfactory;
public class idworker {
protected static final logger log = loggerfactory.getlogger(idworker.class);
private long workerid;
private long datacenterid;
private long sequence = 0l;
private long twepoch = 1288834974657l;
private long workeridbits = 5l;
private long datacenteridbits = 5l;
private long maxworkerid = -1l ^ (-1l << workeridbits);
private long maxdatacenterid = -1l ^ (-1l << datacenteridbits);
private long sequencebits = 12l;
private long workeridshift = sequencebits;
private long datacenteridshift = sequencebits + workeridbits;
private long timestampleftshift = sequencebits + workeridbits + datacenteridbits;
private long sequencemask = -1l ^ (-1l << sequencebits);
private long lasttimestamp = -1l;
public idworker(long workerid, long datacenterid) {
// sanity check for workerid
if (workerid > maxworkerid || workerid < 0) {
throw new illegalargumentexception(string.format("worker id can't be greater than %d or less than 0", maxworkerid));
}
if (datacenterid > maxdatacenterid || datacenterid < 0) {
throw new illegalargumentexception(string.format("datacenter id can't be greater than %d or less than 0", maxdatacenterid));
}
this.workerid = workerid;
this.datacenterid = datacenterid;
log.info(string.format("worker starting. timestamp left shift %d, datacenter id bits %d, worker id bits %d, sequence bits %d, workerid %d", timestampleftshift, datacenteridbits, workeridbits, sequencebits, workerid));
}
public synchronized long nextid() {
long timestamp = timegen();
if (timestamp < lasttimestamp) {
log.error(string.format("clock is moving backwards. rejecting requests until %d.", lasttimestamp));
throw new runtimeexception(string.format("clock moved backwards. refusing to generate id for %d milliseconds", lasttimestamp - timestamp));
}
if (lasttimestamp == timestamp) {
sequence = (sequence + 1) & sequencemask;
if (sequence == 0) {
timestamp = tilnextmillis(lasttimestamp);
}
} else {
sequence = 0l;
}
lasttimestamp = timestamp;
return ((timestamp - twepoch) << timestampleftshift) | (datacenterid << datacenteridshift) | (workerid << workeridshift) | sequence;
}
protected long tilnextmillis(long lasttimestamp) {
long timestamp = timegen();
while (timestamp <= lasttimestamp) {
timestamp = timegen();
}
return timestamp;
}
protected long timegen() {
return system.currenttimemillis();
}
}
测试生成id的测试类,idworkertest.java:
package com.demo.elk;
import java.util.hashset;
import java.util.set;
public class idworkertest {
static class idworkthread implements runnable {
private set<long> set;
private idworker idworker;
public idworkthread(set<long> set, idworker idworker) {
this.set = set;
this.idworker = idworker;
}
public void run() {
while (true) {
long id = idworker.nextid();
system.out.println( real id: + id);
if (!set.add(id)) {
system.out.println(duplicate: + id);
}
}
}
}
public static void main(string[] args) {
set<long> set = new hashset<long>();
final idworker idworker1 = new idworker(0, 0);
final idworker idworker2 = new idworker(1, 0);
thread t1 = new thread(new idworkthread(set, idworker1));
thread t2 = new thread(new idworkthread(set, idworker2));
t1.setdaemon(true);
t2.setdaemon(true);
t1.start();
t2.start();
try {
thread.sleep(30000);
} catch (interruptedexception e) {
e.printstacktrace();
}
}
}
7,总结(1)单实例或者单节点组:
经过500w、1000w的单机表测试,自增id相对uuid来说,自增id主键性能高于uuid,磁盘存储费用比uuid节省一半的钱。所以在单实例上或者单节点组上,使用自增id作为首选主键。
(2)分布式架构场景:
20个节点组下的小型规模的分布式场景,为了快速实现部署,可以采用多花存储费用、牺牲部分性能而使用uuid主键快速部署;
20到200个节点组的中等规模的分布式场景,可以采用自增id+步长的较快速方案。
200以上节点组的大数据下的分布式场景,可以借鉴类似twitter雪花算法构造的全局自增id作为主键。
以上就是mysql 使用自增id主键和uuid 作为主键的优劣比较详细过程(从百万到千万表记录测试)的内容。