雪花算法的使用(工具类utils)
- import org.springframework.beans.factory.annotation.Value;
- import org.springframework.stereotype.Component;
-
- // 雪花算法
- @Component
- public class SnowflakeUtils {
- // Generated ID: 1724603634882318341;
- // Generated ID: 1724603717312974850
- // Generated ID: 1724603717312974851
- public static void main(String[] args) {
- // 创建一个 SnowflakeUtils 实例
- SnowflakeUtils snowflakeUtils = new SnowflakeUtils(1, 1);
- // 生成10个唯一ID并打印
- for (int i = 0; i < 10; i++) {
- long id = snowflakeUtils.nextId();
- System.out.println("Generated ID: " + id);
- }
- }
- // 工作机器ID
- private final long workerId;
-
- public SnowflakeUtils() {
- this.workerId = 1L; // 设置默认值
- this.dataCenterId = 1L; // 设置默认值
- // 初始化雪花算法实例
- }
-
- public SnowflakeUtils(@Value("${snowflake.workerId}") long workerId) {
- this.workerId = workerId;
- // 初始化雪花算法实例
- }
-
- // public SnowflakeUtils(@Value("${snowflake.workerId}") long workerId,@Value("${snowflake.dataCenterId}") long dataCenterId) {
- // this.workerId = workerId;
- // this.dataCenterId = dataCenterId;
- // }
- // 起始的时间戳
- private final long twepoch = 1288834974657L;
- // 机器ID所占的位数
- private final long workerIdBits = 5L;
- // 数据标识ID所占的位数
- private final long dataCenterIdBits = 5L;
- // 支持的最大机器ID,结果是31
- private final long maxWorkerId = -1L ^ (-1L << workerIdBits);
- // 支持的最大数据标识ID,结果是31
- private final long maxDataCenterId = -1L ^ (-1L << dataCenterIdBits);
- // 序列在ID中占的位数
- private final long sequenceBits = 12L;
- // 机器ID的偏移量(12)
- private final long workerIdShift = sequenceBits;
- // 数据标识ID的偏移量(12+5)
- private final long dataCenterIdShift = sequenceBits + workerIdBits;
- // 时间戳的偏移量(12+5+5)
- private final long timestampLeftShift = sequenceBits + workerIdBits + dataCenterIdBits;
- // 生成序列的掩码,这里为4095
- private final long sequenceMask = -1L ^ (-1L << sequenceBits);
- // 数据中心ID
- private long dataCenterId;
-
- // 毫秒内序列
- private long sequence = 0L;
-
- // 上次生成ID的时间截
- private long lastTimestamp = -1L;
-
- public SnowflakeUtils(long workerId, long dataCenterId) {
- if (workerId > maxWorkerId || workerId < 0) {
- throw new IllegalArgumentException("workerId can't be greater than " + maxWorkerId + " or less than 0");
- }
- if (dataCenterId > maxDataCenterId || dataCenterId < 0) {
- throw new IllegalArgumentException("dataCenterId can't be greater than " + maxDataCenterId + " or less than 0");
- }
- this.workerId = workerId;
- this.dataCenterId = dataCenterId;
- }
-
- // 生成ID
- public synchronized long nextId() {
- long timestamp = timeGen();
-
- if (timestamp < lastTimestamp) {
- throw new RuntimeException("Clock moved backwards. Refusing to generate id for " + (lastTimestamp - timestamp) + " milliseconds.");
- }
-
- if (lastTimestamp == timestamp) {
- sequence = (sequence + 1) & sequenceMask;
- if (sequence == 0) {
- timestamp = tilNextMillis(lastTimestamp);
- }
- } else {
- sequence = 0L;
- }
-
- lastTimestamp = timestamp;
-
- return ((timestamp - twepoch) << timestampLeftShift) |
- (dataCenterId << dataCenterIdShift) |
- (workerId << workerIdShift) |
- sequence;
- }
-
- private long tilNextMillis(long lastTimestamp) {
- long timestamp = timeGen();
- while (timestamp <= lastTimestamp) {
- timestamp = timeGen();
- }
- return timestamp;
- }
-
- private long timeGen() {
- return System.currentTimeMillis();
- }
- }
调用雪花算法工具类
long snowflakeUtils= snowflakeUtils.nextId();
雪花算法(Snowflake Algorithm)是一种用于生成唯一ID的分布式算法。它最初是由Twitter开发的,用于生成分布式系统中的唯一标识符。雪花算法的核心思想是将一个64位的整数ID分成多个部分,每个部分表示不同的信息。
雪花算法的结构一般包括:
优点:
缺点:
总体来说,雪花算法是一种简单且高效的分布式ID生成方案,但在特定场景下需要注意其一些缺点。后续再补充。