MySQL实现序列(Sequence)效果以及在Mybatis中如何使用这种策略-阿里云开发者社区

开发者社区> 技术小阿哥> 正文

MySQL实现序列(Sequence)效果以及在Mybatis中如何使用这种策略

简介:
+关注继续查看

前言:

在oracle中一般使用序列(Sequence)来处理主键字段,在MySQL中是没有序列的,但是MySQL有提供了自增长(increment)来实现类似的目的,但也只是自增,而不能设置步长、开始索引、是否循环等。最重要的是一张表只能设置一个字段使用自增,但有的时候我们需要两个或两个以上的字段实现自增(单表多字段自增),MySQL本身是实现不了的,但我们可以用创建一个序列表,使用函数来获取序列的值

一 MySQL中序列的实现

(1)新建一个测试表:

1
2
3
4
5
6
7
8
9
10
11
12
DROP TABLE IF EXISTS `article`;
CREATE TABLE `article` (
  `id` int(11) NOT NULL,
  `namevarchar(100) DEFAULT NULL,
  `author` varchar(50) DEFAULT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
 
-- ----------------------------
-- Records of article
-- ----------------------------
INSERT INTO `article` VALUES ('1''程序猿的自我修养''zifangsky');

注意,这里并没有设置主键自增

(2)添加序列表并添加测试数据:

1
2
3
4
5
6
7
8
9
10
11
12
DROP TABLE IF EXISTS `sequence`;
CREATE TABLE `sequence` (
  `seq_name` varchar(50) NOT NULL,
  `current_val` int(11) NOT NULL,
  `increment_val` int(11) NOT NULL DEFAULT '1',
  PRIMARY KEY (`seq_name`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
 
-- ----------------------------
-- Records of board_event_success
-- ----------------------------
INSERT INTO `sequenceVALUES ('seq_article''0''1');
  • “seq_name”字段表示一个表的的序列,起名最好跟表的名字相关,并且每个表一条数据

  • “current_val”字段表示“seq_name”字段所对应的表的当前最大ID(主键ID)

  • “increment_val”字段表示“seq_name”字段所对应的表的主键ID增长的步长(也就是每次自增+1、+2等)

(3)创建一个用于获取一个表当前最大ID的函数:

1
2
3
4
5
6
7
8
9
10
11
DROP FUNCTION IF EXISTS `currval`;
DELIMITER ;;
CREATE FUNCTION `currval`(v_seq_name VARCHAR(50)) RETURNS int(11)
begin     
    declare value integer;       
    set value = 0;       
    select current_val into value from sequence where seq_name = v_seq_name; 
   return value; 
end
;;
DELIMITER ;

从代码可以看出,这个函数的逻辑很简单,就是根据“seq_name”查询“sequence”这个表的“current_val”这个字段的值

测试:

1
mysql> select currval('seq_article');

很显然,现在输出为0

(4)创建一个用于获取一个表下一个ID的函数:

1
2
3
4
5
6
7
8
9
DROP FUNCTION IF EXISTS `nextval`;
DELIMITER ;;
CREATE FUNCTION `nextval`(v_seq_name VARCHAR(50)) RETURNS int(11)
begin
    update sequence set current_val = current_val + increment_val where seq_name = v_seq_name;
    return currval(v_seq_name);
end
;;
DELIMITER ;

这个函数的逻辑也很简单,先是更新“sequence”这个表中的某一个表的序列值,然后再次查询该序列值作为插入数据时的主键ID

测试:

1
mysql> select nextval('seq_article');

很显然,执行这个函数的结果是1,同时“sequence”这个表中的对应的记录也增加了1

二 Mybatis中的序列使用

使用插件生成一个表对应的Mapper.xml文件时需要修改其生成策略,具体来说就是修改generatorConfig.xml文件,修改一个表的基本数据的生成策略:

1
2
3
4
<table tableName="article" domainObjectName="Article" enableCountByExample="false" enableDeleteByExample="false" enableSelectByExample="false" enableUpdateByExample="false">
    <property name="ignoreQualifiersAtRuntime" value="false"/>
    <generatedKey column="id" sqlStatement="select nextval('seq_article');"/>
</table>

然后运行插件,最后我们可以看到生成的insert方法是这样的:

1
2
3
4
5
6
7
8
9
  <insert id="insert" parameterType="cn.zifangsky.model.Article" >
    <selectKey resultType="java.lang.Integer" keyProperty="id" order="BEFORE" >
      select nextval('seq_article');
    </selectKey>
    insert into article (id, name, author
      )
    values (#{id,jdbcType=INTEGER}, #{name,jdbcType=VARCHAR}, #{author,jdbcType=VARCHAR}
      )
  </insert>

也就是说使用Mybatis插入数据时,它先是通过 nextval 函数查出待插入数据的主键ID之后,再进行数据的插入




本文转自 pangfc 51CTO博客,原文链接:http://blog.51cto.com/983836259/1889590,如需转载请自行联系原作者

版权声明:本文内容由阿里云实名注册用户自发贡献,版权归原作者所有,阿里云开发者社区不拥有其著作权,亦不承担相应法律责任。具体规则请查看《阿里云开发者社区用户服务协议》和《阿里云开发者社区知识产权保护指引》。如果您发现本社区中有涉嫌抄袭的内容,填写侵权投诉表单进行举报,一经查实,本社区将立刻删除涉嫌侵权内容。

相关文章
mysql中使用enum,如何获取所有可能的值
SELECT column_type FROM information_schema. COLUMNS WHERE TABLE_SCHEMA = "数据库名" AND DATA_TYPE = 'enum' AND table_name="表明" AND column_name="列名";   ...
681 0
iOS开发中 关于阿里云服务器的使用与安全策略 韩俊强的博客
使用背景:         云服务已经很多年了,早期没能加入使用云大军中的一员,后来后悔莫及。2015年记得当时没办法租用的虚拟主机三天两天挂了,导致我认认真真的考虑了一次,觉得还是要使用云服务器! 从免费的主机屋学习版到各种虚拟机的实验,再到之前是用300元左右买的别人的虚拟主机,空间有几G,感觉还行,正好又值他们搞活动,买两年送一年!预存还有返还!心动了,就没有任何考虑就预存了一千块! 开始的几个月感觉还行,速度什么的还过得去,就没去管网站的事了。
1267 0
OpenKruise v0.5.0 版本发布,支持无损的流式分批发布策略
目前在阿里巴巴内部云原生环境中,绝大部分应用都统一使用 OpenKruise 的能力做 Pod 部署、发布管理,而不少业界公司和阿里云上客户由于 K8s 原生 Deployment 等负载不能完全满足需求,也转而采用 OpenKruise 作为应用部署载体。
215 0
实战课堂 | 科技减灾 如何使用Geo-SQL实现洪灾承灾体损失评估?
洪涝灾害是我国目前面临的最主要的自然灾害,利用洪涝灾害承灾体损失综合评估模型,对灾害损失率和损失价值分布进行科学地计算,对于指导洪涝救灾、建立灾害预警机制、加强洪涝灾害成灾机制的研究,建立和完善更科学、更准确的洪灾损失评估预测体系具有重要的意义。
285 0
block使用小结、在arc中使用block、如何防止循环引用(zz)
<div class="articalTag" id="sina_keyword_ad_area" style="width:690px; clear:both; word-break:break-all; line-height:20px; color:rgb(70,70,70); font-family:Verdana,宋体,sans-serif"> <table style="ma
1104 0
MyBatis Generator(MBG)PostgreSQL使用说明 区分大小写敏感
PostgreSQL使用说明区分大小写敏感 PostgreSQL对所有数据库标识符(表名,模式名,列名等)区分大小写。此外,PostgreSQL对所有小写字母的所有标识符都有不同的偏好。如果您使用PostgreSQL的所有小写标识符,那么MyBatis Generator将找到表并写入正确的SQL,而无需额外考虑。
1417 0
面试7 GC机制中如何判断一个对象是否任在使用
GC 通过在使用的根引用遍历所有引用的对象实例,当一个对象不能被遍历时,将被视为不能被使用。博客内容仅代表个人观点,如发现阐述有误,麻烦指正,谢谢!
539 0
8434
文章
0
问答
文章排行榜
最热
最新
相关电子书
更多
文娱运维技术
立即下载
《SaaS模式云原生数据仓库应用场景实践》
立即下载
《看见新力量:二》电子书
立即下载