雪花算法Snowflake,看完秒懂!
创作时间:
作者:
@小白创作中心
雪花算法Snowflake,看完秒懂!
引用
CSDN
1.
https://m.blog.csdn.net/qq_56158663/article/details/145829364
准备好,咱要用一种不正经但又很认真的方式,来扒一扒雪花算法的底裤! 😜
雪花算法:一个“高富帅”ID生成器
想象一下,你是一个皇帝,要给你的子民们发身份证。如果每个人都叫“张三”、“李四”,那肯定乱套了!所以,你需要一个能保证每个人身份证号都独一无二的算法。雪花算法,就是这个“高富帅”身份证生成器!😎
雪花算法的“身世背景”
雪花算法,英文名叫 Snowflake,听起来就很高冷。它最初是 Twitter 为了解决分布式系统中的ID生成问题而设计的。在分布式世界里,有很多台电脑一起干活,如果每台电脑都自己生成ID,很容易撞衫(ID重复)。雪花算法就是来避免这种尴尬的!
雪花ID的“构成”
雪花ID是一个64位的二进制数字,就像一个人的身份证号一样,每一段都有特殊的含义:
+---+------------------------+----------------+-----------+-----------+
| 1 | 41 | 5 | 5 | 12 |
+---+------------------------+----------------+-----------+-----------+
| | timestamp | datacenterId | workerId | sequence |
+---+------------------------+----------------+-----------+-----------+
- 符号位 (1 bit):永远是0,因为我们只想要正数ID。就像一个人的性别,要么男,要么女,这里永远是“正”!💪
- 时间戳 (41 bits):记录了从某个特定时间(Epoch)开始,到现在的毫秒数。这就像一个人的出生日期,越晚出生,这个数字越大。41位能用69年,够你用了!🎂
- 数据中心ID (5 bits):标识这个ID是在哪个数据中心生成的。就像一个人的户籍所在地,北京、上海、广州,总得有个地方落户吧?最多支持32个数据中心。🏢
- 机器ID (5 bits):标识这个ID是在数据中心里的哪台机器上生成的。就像一个人的具体住址,几栋几单元几零几。每个数据中心最多支持32台机器。💻
- 序列号 (12 bits):如果同一毫秒内,同一台机器要生成多个ID,就靠这个序列号来区分了。就像一个人的名字,如果同一天出生的人太多,就得起个不一样的名字。每毫秒最多可以生成4096个ID。🔢
雪花算法在SpringBoot中的使用,这里使用的是hutool工具包封装的雪花算法
1. 添加 Hutool 依赖
在 pom.xml
文件中添加 Hutool 依赖:
<dependency>
<groupId>cn.hutool</groupId>
<artifactId>hutool-all</artifactId>
<version>5.8.24</version>
</dependency>
2. 创建 SnowflakeIdWorker 类 (使用 Hutool)
import cn.hutool.core.lang.Snowflake;
import cn.hutool.core.util.IdUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;
import javax.annotation.PostConstruct;
@Component
@Slf4j
public class SnowflakeIdWorker {
@Value("${snowflake.datacenter-id:0}") // 默认值为 0
private long datacenterId;
@Value("${snowflake.worker-id:0}") // 默认值为 0
private long workerId;
private Snowflake snowflake; // Hutool 提供的雪花算法工具类
@PostConstruct
public void init() {
// 创建 Snowflake 对象,传入数据中心ID和机器ID
snowflake = IdUtil.createSnowflake(datacenterId, workerId);
log.info("SnowflakeIdWorker started with datacenterId: {}, workerId: {}", datacenterId, workerId);
}
public long nextId() {
// 生成下一个 ID
return snowflake.nextId();
}
public String nextIdStr() {
// 生成下一个 ID (String 类型)
return snowflake.nextIdStr();
}
}
代码解释:
snowflake = IdUtil.createSnowflake(datacenterId, workerId);
:使用IdUtil.createSnowflake()
方法创建一个 Snowflake 对象,传入数据中心 ID 和机器 ID。snowflake.nextId()
:调用 Snowflake 对象的nextId()
方法生成下一个 long 类型的 ID。snowflake.nextIdStr()
:调用 Snowflake 对象的nextIdStr()
方法生成下一个 String 类型的 ID。
3. 在 application.yml
中配置 datacenterId
和 workerId
(可选)
# application.yml
snowflake:
datacenter-id: 1
worker-id: 1
4. 使用 SnowflakeIdWorker
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
@RestController
public class IdController {
@Autowired
private SnowflakeIdWorker idWorker;
@GetMapping("/nextId")
public long nextId() {
long id = idWorker.nextId();
System.out.println("生成的 long 型 ID: " + id); // 输出结果
return id;
}
@GetMapping("/nextIdStr")
public String nextIdStr() {
String id = idWorker.nextIdStr();
System.out.println("生成的 String 型 ID: " + id); // 输出结果
return id;
}
}
代码解释:
System.out.println("生成的 long 型 ID: " + id);
:在控制台输出生成的 long 型 ID。System.out.println("生成的 String 型 ID: " + id);
:在控制台输出生成的 String 型 ID。
5. 运行 Spring Boot 应用并测试
启动 Spring Boot 应用,访问以下 URL:
http://localhost:8080/nextId
http://localhost:8080/nextIdStr
输出结果:
生成的 long 型 ID: 1699876543210987654
生成的 String 型 ID: 1699876543210987655
雪花算法的“工作原理”
- 获取当前时间戳:就像看了一眼现在的日期。⌚
- 分配数据中心ID和机器ID:就像确定了你的户籍所在地和具体住址。🏠
- 生成序列号:如果同一毫秒内要生成多个ID,就递增序列号。就像同一天出生的宝宝,按顺序起名字。👶
- 把这些信息拼起来:用位运算把时间戳、数据中心ID、机器ID和序列号拼成一个64位的数字。就像把你的出生日期、户籍所在地、住址和名字都写在身份证上。
雪花算法的“优点”
- 全局唯一:只要数据中心ID和机器ID不重复,生成的ID就绝对不会重复。就像每个人的身份证号都是独一无二的。💯
- 高性能:生成ID的速度非常快,因为主要靠位运算。就像闪电侠一样,嗖嗖嗖就生成一个ID。⚡
- 趋势递增:生成的ID总体上是递增的,方便数据库索引。就像排队一样,先来后到,井然有序。🚶
- 简单易用:算法逻辑简单,容易实现。就像傻瓜相机一样,一按快门就能拍照。📸
雪花算法的“缺点”
- 依赖时钟:如果服务器的时钟发生回拨,可能会生成重复的ID。就像穿越回过去,历史可能会被改变。🕰️
- 需要配置:需要为每个数据中心和机器分配唯一的ID,增加了部署的复杂性。就像开公司一样,需要注册地址和营业执照。🏢
时钟回拨:雪花算法的“阿喀琉斯之踵”
时钟回拨是指服务器的时钟突然变慢,导致时间戳变小。这可能会导致雪花算法生成重复的ID。
如何应对时钟回拨?
- 拒绝服务:如果发现时钟回拨,直接拒绝生成ID。就像发现穿越,直接阻止。🚫
- 等待:如果回拨时间不长,就等待一段时间,让时钟追上来。就像堵车一样,等等就好了。🚗
- 使用备用方案:如果回拨时间太长,就切换到备用的ID生成方案,比如UUID。就像备胎一样,关键时刻能顶上。🚗💨
- 调整时间戳:如果回拨时间很短,可以把时间戳调整到上次生成ID的时间戳。就像把表拨快一点,假装没事发生。⌚➡️
总结
雪花算法是一个简单、高效、可靠的分布式ID生成算法。虽然它有一些缺点,但只要我们注意时钟回拨问题,并采取相应的措施,就能让它在分布式系统中发挥巨大的作用! 🚀
希望这个幽默版的讲解能让你更好地理解雪花算法! 记住,技术再高深,也要用轻松的心态去学习! 😉
热门推荐
子公司破产清算对母公司股价的影响分析
宁国到龙里的长途客车班次查询表(乘车路线+票价/发车时刻表+汽车大巴车)
金价大跳水,专家解析黄金投资新策略
长期低碳饮食会影响身体代谢吗?
市政污水管施工全解析:从设计到竣工的每一步
情侣装如何选择 情侣装搭配小技巧
痉挛型脑瘫怎么检查
如何分配婚后房屋财产?不同国家的法律规定有何差异?
五险一金的法律用途及其社会保障功能解析
反物质火箭可使星际旅行成为现实 其推进力可提高300倍
金融风险控制中流动性风险管理与应对措施
2024上半年口碑最好的10部剧,看过一半以上的,绝对是慧眼识珠!
飞钱:古代中国的“汇票”与经济创新
汉字"论"的详细解释
夫妻互相担保贷款可以吗?法律角度解析
双ISP代理架构下的跨境物流信息实时追踪系统
公积金消费贷款:法律规定与实践解析
阿尔兹海默症检查哪些项目
被打后的民事赔偿标准与处理方法
鱼油是什么
证券公司靠什么盈利?证券公司的盈利模式和市场竞争状况如何?
低空空域各类飞行器大盘点
康熙的儿子们及其不同结局
如何评估新能源汽车产业链各环节的风险?
如何构建积极工作环境:促进员工满意度与认同感?
台儿庄战役:国军伤亡5万,日军伤亡1万,为什么还能称为大捷?
GIS前端开发需要学什么
恶女的告白:人性深渊与救赎之光
羊驼究竟是羊还是驼(正确答案)
合肥高新区聚力建设世界领先科技园区