java 生成11位唯一id
时间: 2025-06-12 20:06:38 浏览: 2
### Java 中生成 11 位唯一 ID 的实现方法
在 Java 中生成固定长度的唯一 ID 是一种常见需求,可以通过多种方式实现。以下是几种可能的方法及其对应的示例代码。
#### 方法一:基于时间戳和随机数组合
通过将当前时间戳与随机数相结合,并截取前 11 位字符来生成唯一 ID。这种方法简单易懂,适合低并发场景。
```java
import java.util.concurrent.ThreadLocalRandom;
public class ElevenDigitIdGenerator {
public static String generateUniqueId() {
long timestamp = System.currentTimeMillis();
int randomPart = ThreadLocalRandom.current().nextInt(1000);
String combined = Long.toString(timestamp) + Integer.toString(randomPart);
return combined.substring(combined.length() - 11); // 截取最后 11 位
}
public static void main(String[] args) {
for (int i = 0; i < 5; i++) {
System.out.println("Generated ID: " + generateUniqueId());
}
}
}
```
此方法利用 `System.currentTimeMillis()` 和随机数生成器生成一个字符串并截取其后 11 位[^1]。
---
#### 方法二:自增计数器结合哈希
使用原子整数(`AtomicInteger`)作为计数器,每次调用时增加计数器值,并将其转换为十六进制表示形式。为了确保唯一性,还可以加入其他字段如主机名或进程 ID。
```java
import java.util.concurrent.atomic.AtomicInteger;
public class ElevenDigitCounterBasedIdGenerator {
private static final AtomicInteger counter = new AtomicInteger(0);
public static String generateUniqueId() {
int countValue = counter.getAndIncrement();
String hexString = Integer.toHexString(countValue);
while (hexString.length() < 11) { // 补齐到 11 位
hexString = "0" + hexString;
}
return hexString.substring(hexString.length() - 11); // 取最后 11 位
}
public static void main(String[] args) {
for (int i = 0; i < 5; i++) {
System.out.println("Generated ID: " + generateUniqueId());
}
}
}
```
该方法依赖于线程安全的 `AtomicInteger` 来保证高并发环境下的安全性[^2]。
---
#### 方法三:Snowflake 算法变体
Snowflake 算法是一种高效的分布式 ID 生成算法,通常由时间戳、机器 ID 和序列号组成。如果需要生成 11 位的唯一 ID,则需调整各部分的比例以适应目标长度。
```java
public class ElevenDigitSnowflakeIdGenerator {
private final long workerIdBits = 5L; // 工作节点 ID 所占位数
private final long sequenceBits = 6L; // 序列号所占位数
private final long maxWorkerId = ~(-1L << workerIdBits); // 最大工作节点 ID
private final long maxSequence = ~(-1L << sequenceBits); // 最大序列号
private final long workerIdShift = sequenceBits; // 工作节点左移位数
private final long timestampLeftShift = sequenceBits + workerIdBits; // 时间戳左移位数
private long lastTimestamp = -1L;
private long sequence = 0L;
private final long workerId;
public ElevenDigitSnowflakeIdGenerator(long workerId) {
if (workerId > maxWorkerId || workerId < 0) {
throw new IllegalArgumentException("worker Id can't be greater than %d or less than 0".formatted(maxWorkerId));
}
this.workerId = workerId;
}
public synchronized String nextIdStr() {
long timestamp = timeGen();
if (timestamp < lastTimestamp) {
throw new RuntimeException("Clock moved backwards");
}
if (lastTimestamp == timestamp) {
sequence = (sequence + 1) & maxSequence;
if (sequence == 0) {
timestamp = tilNextMillis(lastTimestamp);
}
} else {
sequence = 0L;
}
lastTimestamp = timestamp;
long id = ((timestamp & 0xFFFFFFFFFFFFFL) >> 22) | (workerId << workerIdShift) | sequence;
return Long.toString(id).substring(Long.toString(id).length() - 11);
}
protected long tilNextMillis(long lastTimestamp) {
long timestamp = timeGen();
while (timestamp <= lastTimestamp) {
timestamp = timeGen();
}
return timestamp;
}
protected long timeGen() {
return System.currentTimeMillis();
}
public static void main(String[] args) {
ElevenDigitSnowflakeIdGenerator generator = new ElevenDigitSnowflakeIdGenerator(1);
for (int i = 0; i < 5; i++) {
System.out.println("Generated ID: " + generator.nextIdStr());
}
}
}
```
这段代码实现了 Snowflake 算法的一个简化版本,其中时间戳、工作节点 ID 和序列号共同构成了最终的 11 位 ID[^5]。
---
#### 方法四:UUID 转换
虽然标准 UUID 长度超过 11 位,但可通过对其散列化或将部分内容提取出来的方式缩短至所需长度。
```java
import java.util.UUID;
public class ElevenDigitUuidBasedIdGenerator {
public static String generateUniqueId() {
String uuid = UUID.randomUUID().toString().replaceAll("-", "");
return uuid.substring(0, Math.min(uuid.length(), 11)); // 提取前 11 位
}
public static void main(String[] args) {
for (int i = 0; i < 5; i++) {
System.out.println("Generated ID: " + generateUniqueId());
}
}
}
```
尽管这种方式可能会降低唯一性的概率,但在某些情况下仍然适用[^3]。
---
### 总结
以上四种方法分别适用于不同场景:
- **方法一**:适合简单的单机应用;
- **方法二**:适合需要高性能且无冲突风险的应用;
- **方法三**:推荐用于分布式系统中的唯一 ID 生产;
- **方法四**:仅当对性能要求不高时考虑使用。
阅读全文
相关推荐
















