MySQL 插入与自增主键值相等的字段 与 高并发下保证数据准确的实验
场景描述: 表t2 中 有 自增主键 id 和 字段v 当插入记录的时候 要求 v与id 的值相等(按理来说这样的字段是需要拆表的,但是业务场景是 只有某些行相等 )
在网上搜的一种办法是 先获取自增ID
SELECT max(id)+1 from t2
然后给v字段插入获取到的值
但是这样的做法在有删除行+调整过自增值的表中是不准确的
于是换个思路 从 information_schema 下手 读取表的信息
INSERT INTO `t2`
VALUES
(
NULL,
(
SELECT
`AUTO_INCREMENT`
FROM
`information_schema`.`TABLES`
WHERE
`TABLE_SCHEMA` = 'test'
AND `TABLE_NAME` = 't2'
)
);
功能是实现了 但是真的安全么
于是写个PHP文件
<?php
$sql = "INSERT INTO `t2` VALUES(NULL ,(SELECT `AUTO_INCREMENT` FROM `information_schema`.`TABLES` WHERE `TABLE_SCHEMA` = 'test' AND `TABLE_NAME`='t2'));"; $link = mysql_connect("localhost", "root", "") or die("Could not connect: " . mysql_error());
mysql_select_db("test");
mysql_query($sql);
mysql_close($link);
?>
用ab工具测试
ab -n 50000 -c 20 http://localhost/my.php
结果是:大量的行出现了 v 和 id 不相等的情况(select * from t2 where id != v;)
改写下 PHP
<?php
$sql = "INSERT INTO `t2` VALUES(NULL ,(SELECT `AUTO_INCREMENT` FROM `information_schema`.`TABLES` WHERE `TABLE_SCHEMA` = 'test' AND `TABLE_NAME`='t2'));"; $link = mysql_connect("localhost", "root", "") or die("Could not connect: " . mysql_error());
mysql_select_db("test");
mysql_query('START TRANSACTION'); #开始事务
mysql_query($sql);
$id = mysql_insert_id();
$res = mysql_query("SELECT `v` FROM `t2` WHERE id= ".$id); if (!$res) {
mysql_close($link);
die;
} $row = mysql_fetch_assoc($res);
if($row['v'] != $id){
mysql_query(' ROLLBACK '); #回滚事务
}
mysql_query('COMMIT'); #提交事务
mysql_close($link);
?>
再使用AB测试,这次速度变慢了 但是结果是都是正确的
MySQL 插入与自增主键值相等的字段 与 高并发下保证数据准确的实验的更多相关文章
- 关于mybatis用mysql时,插入返回自增主键的问题
公司决定新项目用mybatis,虽然这个以前学过但是一直没用过都忘得差不多了,而且项目比较紧,也没时间去系统点的学一学,只好很粗略的百度达到能用的程度就行了. 其中涉及到插入实体要求返回主键id的问题 ...
- Mybatis useGeneratedKeys 填充自增主键值(使用Mysql)的原理分析
一.Mybatis配置 <insert id="insert" parameterType="com.test.TestDO" keyProperty=& ...
- MySQL 中的自增主键
MySQL 的主键可以是自增的,那么如果在断电重启后新增的值还会延续断电前的自增值吗?自增值默认为1,那么可不可以改变呢?下面就说一下 MySQL 的自增值. 特点 保存策略 1.如果存储引擎是 My ...
- java面试一日一题:mysql中的自增主键
问题:请讲下mysql中的自增主键 分析:该问题主要考察对mysql中自增主键的掌握,使用场景及如何设置 回答要点: 主要从以下几点去考虑 1.什么自增主键 2.使用场景是什么: 3.innodb_a ...
- MyBatis映射文件1(增删改、insert获取自增主键值)
增删改 Mybatis为我们提供了<insert>.<update>.<delete>标签来对应增删改操作 在接口中写增删改的抽象方法 void addEmp(Em ...
- mysql数据库插入数据获取自增主键的三种方式(jdbc PreparedStatement方式、mybatis useGeneratedKeys方式、mybatis selectKey方式)
通常来说对于mysql数据库插入数据获取主键的方法是采用selectKey的方式,特别是当你持久层使用mybatis框架的时候. 本文除此之外介绍其它两种获取主键的方式. 为了方便描述我们先建一张my ...
- SQL Server 插入数据后获得自增主键值
通过SQLServer系统自带函数获取 String sql = "insert into goods values('" + TextBox1.Text + "',&q ...
- mycat分布式mysql中间件(自增主键)
一.全局序列号 全局序列号是MyCAT提供的一个新功能,为了实现分库分表情况下,表的主键是全局唯一,而默认的MySQL的自增长主键无法满足这个要求.全局序列号的语法符合标准SQL规范,其格式为:nex ...
- mysql的innodb自增主键为什么不是连续的
图1 图1中是表t原有的数据,这个时候我们执行show create table t会看到如下输出,如图二所示现在的自增值是2,也就是下一个不指定主键值的插入的数据的主键就是2 图2 Innodb引擎 ...
随机推荐
- JVM的相关知识整理和学习--(转载)
JVM是虚拟机,也是一种规范,他遵循着冯·诺依曼体系结构的设计原理.冯·诺依曼体系结构中,指出计算机处理的数据和指令都是二进制数,采用存储程序方式不加区分的存储在同一个存储器里,并且顺序执行,指令由操 ...
- Charles是mac的iddler抓包工具
windows下面我们经常使用 Fiddler 抓包工具进行代理等一系列操作.然而,在 Mac 下 http://en.softonic.com/s/java-se-6:mac
- Maven3路程(五)用Maven创建Hibernate项目
本文将用Maven3.Hibernate3.6.Oracle10g整合,作为例子. 环境清单: 1.Maven3.0.5 2.Hibernate3.6.5 Final 3.JDK1.7.0.11 4. ...
- dom4j API使用简介
dom4j API使用简介 功能简介 dom4j是一个Java的XML API,类似于jdom,用来读写XML文件的.dom4j是一个非常非常优秀的Java XML API,具有性能优异.功能强大和极 ...
- eclipse中字母大小写转换快捷键
ctrl+shift+x 转为大写 ctrl+shift+y 转为小写
- hadoop数据容易出现错误的地方
最近在搞关于数据分析的项目,做了一点总结. 下图是系统的数据流向.容易出现错误的地方.1.数据进入hadoop仓库有四种来源,这四种是最基本的数据,简称ods,original data source ...
- boost多边形交集、并集
交集:http://www.boost.org/doc/libs/1_56_0/libs/geometry/doc/html/geometry/reference/algorithms/interse ...
- 多核模糊C均值聚类
摘要: 针对于单一核在处理多数据源和异构数据源方面的不足,多核方法应运而生.本文是将多核方法应用于FCM算法,并对算法做以详细介绍,进而采用MATLAB实现. 在这之前,我们已成功将核方法应用于FCM ...
- exp/imp使用
[sql]view plaincopy 1.EXP: 1.完全: EXP SYSTEM/MANAGER BUFFER=64000 FILE=C:\FULL.DMP FULL=Y 如果要执行完 ...
- 使用Rxjava缓存请求
最近,我尝试使用RxJava开发了一款闲时备份app.我必须承认,一旦你get到了正确的方式,RxJava几乎感觉就像作弊.一切看起来更简洁,多个请求能够被组合,且非常容易控制.通过在UI线程观察和在 ...