乐观锁:故名思意,十分乐观,它总是认为不会出现问题,无论干什么不去上锁!如果出来问题,再次更新值测试。
version:每次更新带一个版本号
悲观锁:顾名思义,十分悲观,它总是认为总会出现问题,无论干什么都会去上锁,再去操作。
乐观锁的实现通常包括以下步骤:
- 读取记录时,获取当前的版本号(version)。
- 在更新记录时,将这个版本号(version)一同传递。
- 执行更新操作时,设置
version = newVersion
的条件为version = oldVersion
。 - 如果版本号不匹配,则更新失败。
#乐观锁1.先查询,获取版本号 version=1
--A
update user set name = "txs",version + 1
where id = 2 and version = 1
--B线程抢先完成,这个时候version=2,会导致A线程更新失败
update user set name = "txs",version + 1
where id = 2 and version = 1
测试一下Mybatis——plus的乐观锁插件
1.先给数据库加上version列,默认值为1
//.config.
@MapperScan("com.example.demo.mapper")//扫描我们的mapper文件夹下的所有接口
@Configuration//声明为配置类
public class MybatisPlusConfig {
//注册乐观锁插件
@Bean
public OptimisticLockerInterceptor optimisticLockerInterceptor(){
return new OptimisticLockerInterceptor();
}
}
2.实体类加对应字段
@Version//乐观锁
private Integer version;
}
3.注册组件
//.config.
@MapperScan("com.example.demo.mapper")//扫描我们的mapper文件夹下的所有接口
@Configuration//声明为配置类
public class MybatisPlusConfig {
//注册乐观锁插件
@Bean
public OptimisticLockerInterceptor optimisticLockerInterceptor(){
return new OptimisticLockerInterceptor();
}
}
测试乐观锁
//测试乐观锁
@Test
public void testOptimisticLocker1(){
//1.查询用户信息
User user=userMapper.selectById(1);
//2.修改用户信息
user.setName("txs");
user.setEmail("2109060216");
int result=userMapper.updateById(user);
System.out.println(user);
}
//测试乐观锁失败!多线程
@Test
public void testOptimisticLocker2(){
//模拟线程1
User user1=userMapper.selectById(1);
user1.setName("txs");
user1.setEmail("2109060216@qq.com");
//模拟线程2执行了插队操作
User user2=userMapper.selectById(1);
user2.setName("gem");
user2.setEmail("777@gem.com");
userMapper.updateById(user2);
//回到线程1
userMapper.updateById(user1);
}