业务解决
2026/1/30大约 2 分钟
有一个学生类,按分数排序,再按学号排序如何实现?
方法1:实现 Comparable(最推荐)
public class Student implements Comparable<Student> {
private int id;
private int score;
@Override
public int compareTo(Student o) {
int r = Integer.compare(o.score, this.score); // 分数降序
return r != 0 ? r : Integer.compare(this.id, o.id); // 学号升序
}
}方法2:Comparator(不改类时使用)
Collections.sort(list,
(a, b) -> a.score != b.score ?
Integer.compare(b.score, a.score) :
Integer.compare(a.id, b.id)
);秒杀超卖问题怎么解决?
回答:
秒杀超卖是高并发场景下的典型问题,可通过以下多层级方案解决:
1. 数据库层面
- 乐观锁:使用version字段或CAS机制,更新时检查版本号
UPDATE product SET stock = stock - 1 WHERE id = ? AND stock > 0 AND version = ? - 悲观锁:使用SELECT FOR UPDATE锁定数据,确保同一时间只有一个事务能修改
BEGIN TRANSACTION; SELECT stock FROM product WHERE id = ? FOR UPDATE; -- 检查库存并更新 UPDATE product SET stock = stock - 1 WHERE id = ? AND stock > 0; COMMIT;
2. 应用层面
- Redis预减库存:秒杀前将库存加载到Redis,请求时先在Redis中扣减,成功后再写入数据库
// Redis扣减库存 Long stock = redisTemplate.opsForValue().decrement("product:stock:" + productId); if (stock < 0) { // 库存不足,回滚 redisTemplate.opsForValue().increment("product:stock:" + productId); return "库存不足"; } // 异步写入数据库 - 分布式锁:使用Redis或ZooKeeper实现分布式锁,确保同一商品同一时间只有一个请求能处理
3. 架构层面
- 限流削峰:使用令牌桶、漏桶算法或消息队列(如RabbitMQ)限流,控制请求速率
- 分层过滤:前端层(验证码)、应用层(Redis预减)、数据库层(最终一致性)
- 异步处理:使用消息队列异步处理订单,提高系统吞吐量
4. 业务层面
- 库存预热:秒杀前将商品库存加载到缓存
- 阶梯释放:分批次释放库存,避免瞬间高并发
- 防重复提交:使用token机制防止重复提交请求