Java 没有使用序列的数字主键;如何获得下一个值?

Java 没有使用序列的数字主键;如何获得下一个值?,java,jpa,primary-key,Java,Jpa,Primary Key,我知道应该使用数据库序列来获取表上下一个键的值(让我们假设一个单列数字主键),但是如果不使用序列,您是否看到以下代码有任何明显的代码气味(代码是Java for JPA,但模式与语言和技术无关): boolean=false; int _i=0; 而((!havesucceed)&&(_i++

我知道应该使用数据库序列来获取表上下一个键的值(让我们假设一个单列数字主键),但是如果不使用序列,您是否看到以下代码有任何明显的代码气味(代码是Java for JPA,但模式与语言和技术无关):

boolean=false;
int _i=0;
而((!havesucceed)&&(_i++调试(“ConstraintValidationException,”+((i这看起来不是线程安全的。
您应该以线程安全的方式:

  • 锁定用户表
  • 读取当前最大值(id)
  • 添加1并将其用作下一个id
  • 打开桌子
这近似于数据库中发生的自动增量

如果无法锁定表,请同步该方法,使其
静态同步
或使用
静态
锁定对象,例如:

 private static final Object lock = new Object();

 void yourMethod() {
     synchronized (lock) {
         // your code here
     }
 }

如果您的服务器有多个实例在运行,这种方法是不够的。

如果您费心在访问时重试,为什么不在创建语句时将“方法”设置为CONCUR_READ_ONLY或CONCUR_Updateable with interface“Connection”。createStatement()。 数据库本身是控制大多数读取并发性的因素,但是连接可以告诉数据库作为查询的一部分如何读取它。我不明白,为什么在“如果有可能”会发生访问问题异常而不是任何读取并发性问题的情况下,还要麻烦循环。
Niether我能理解为什么你想要如此不区分数据值吗?如果你正在创建一个用户,你应该首先检查用户是否存在,然后中止该过程,并向预期的新用户发送一条消息“选择另一个用户名”e.t.c.

谢谢,我没有明确提到它,但我想避免锁定表。但是我不清楚为什么N个用户会导致代码执行N+1数据库查询。@约翰:这是一种有趣的方法……CONCUR\u READ\u只适用于一条语句。a行和B行发出两条单独的语句。不清楚对于我来说,如何使用CONCUR_READ_ONLY来确保在代码执行到达第B行时,在A行中计算的最大值仍然有效。
 private static final Object lock = new Object();

 void yourMethod() {
     synchronized (lock) {
         // your code here
     }
 }