java生成一天内不重复的随机4位数字编号

有个需求需要生成不重复4位数字编号,格式是 天 + 4位数字。

实现思路:每天首次获取随机字符串时把所有的数字生成放入缓存中。然后随机从列表中取一条数据,然后更新缓存中的数据。这样就能保住每次拿到的数据不重复

废话不多说直接上代码

public String generate(String key) {
    String redisKey = "code:" + DateUtil.format(new Date(),"dd");
    //获取缓存中未被使用的编号
    List<String> values = redisCache.getCacheObject(redisKey);
    if(CollectionUtil.isEmpty(values)){
        //缓存中的数据为空 则生成0000- 9999放到缓存
        values = new ArrayList<>();
        int i = 0;
        while (i <= 9999){
            values.add(String.format("%1$04d", i));
            i++;
        }
    }
    //生成0 ~ values长度 随机数
    Random random = new Random();
    int index = random.nextInt(values.size() - 1);
    String code = values.get(index);
    //删除已经使用的编号 更新到缓存中
    values.remove(index);
    redisCache.setCacheObject(redisKey, values,1, TimeUnit.DAYS);
    return code;
}

<think>好的,我需要帮助用户解决如何使用Hutool生成唯一的随机字符串的问题。首先,用户提到他们想生成重复随机字符串,并且需要示例代码。根据用户提供的引用内容,我需要结合Hutool的同工具类来实现这一点。 首先,用户提供的引用中提到了NanoId类和RandomUtil类。引用[2]里提到NanoId可以生成纳米字符串,而RandomUtil可以生成随机字符串。但RandomUtil生成随机字符串可能存在重复,尤其是在高并发或大量生成的情况下。因此,我需要考虑如何结合这两个工具来确保唯一性。 NanoID本身设计上具有较低的碰撞概率,适合生成唯一ID。而如果用户需要更长的字符串或者自定义字符集,可能需要结合其他方法。比如,使用NanoId生成基础ID,再拼接时间戳或随机字符串,这样可以进一步降低重复的可能性。 另外,引用[3]提到验证码的生成,可能涉及存储和校验,但用户的问题主要是生成而非存储。过,如果用户需要确保绝对唯一,可能需要将生成的字符串存储在数据库或缓存中,每次生成时检查是否存在。但这可能增加复杂性和性能开销,所以需要权衡。 接下来,我需要提供具体的代码示例。根据引用[2],使用NanoId.randomNanoId()可以直接生成,而RandomUtil.randomString可以生成指定长度的字符串。但如何确保唯一呢?可能需要结合两者,或者使用更长的长度,或者添加时间戳。 例如,可以生成NanoID作为基础,再加上当前时间戳的哈希值,或者使用UUID结合Hutool的工具。过Hutool的UUID工具可能更直接。用户可能没有提到UUID,但这也是一个选项。 另外,考虑高并发场景,单靠随机生成可能够,需要引入某种机制确保唯一性。比如,使用分布式唯一ID生成策略,但Hutool可能没有内置的分布式ID生成器,所以可能需要结合数据库自增ID或其他方法。 综合来看,最直接的Hutool方案是使用NanoID,因为其设计上唯一性较好。如果用户需要更高的唯一性,可以组合NanoID和时间戳,或者使用UUID。 现在需要编写示例代码。例如: 1. 使用NanoId生成唯一ID: String nanoId = NanoId.randomNanoId(); 2. 使用RandomUtil生成较长随机字符串,并拼接时间戳: String randomStr = RandomUtil.randomString(32); String uniqueStr = randomStr + System.currentTimeMillis(); 但这样可能够,因为时间戳在同一毫秒内可能重复。或者使用SecureRandom来增加熵,但Hutool的RandomUtil是否基于SecureRandom?根据文档,RandomUtil默认使用安全的Random,但可能需要确认。 另外,Hutool的ObjectId也是一个选项,生成类似MongoDB的ObjectId,具有时间戳和机器标识,确保唯一性。过用户可能没有提到这个,但可以建议。 总结步骤: - 推荐使用NanoId,因为其唯一性较好。 - 如果长度允许,生成更长的字符串,减少碰撞概率。 - 组合时间戳或使用UUID。 然后给出代码示例,如使用NanoId、RandomUtil生成较长字符串,或者结合两者。 同时需要提醒用户,理论上绝对唯一需要全局唯一性保证,可能需要结合数据库或分布式ID生成方案,但Hutool本身可能无法完全保证。 最后,相关问题可能涉及如何确保唯一性、Hutool的其他ID生成方法、性能考虑等。</think>### 使用 Hutool 生成唯一随机字符串的方法 要生成重复随机字符串,可以通过以下两种方式实现: --- #### 方法一:使用 `NanoId`(推荐) **原理**:NanoID 是一种轻量级的唯一 ID 生成算法,其碰撞概率极低(默认使用 21 字符长度时需生成超过 10 亿次才可能重复)[^2]。 **示例代码**: ```java import cn.hutool.core.lang.id.NanoId; // 生成默认长度的 NanoID(21 字符) String nanoId = NanoId.randomNanoId(); // 生成自定义长度的 NanoID(例如 32 字符) String customNanoId = NanoId.randomNanoId(32); ``` --- #### 方法二:组合 `RandomUtil` 与唯一标识 **原理**:通过 `RandomUtil` 生成随机字符串,再拼接时间戳或唯一标识(如 UUID)以增强唯一性。 **示例代码**: ```java import cn.hutool.core.util.RandomUtil; import cn.hutool.core.lang.UUID; // 生成 20 随机字符串 + UUID 后缀 String randomStr = RandomUtil.randomString(20) + UUID.fastUUID().toString().replace("-", ""); // 生成 30 随机字符串 + 时间戳 String timestampStr = String.valueOf(System.currentTimeMillis()); String uniqueStr = RandomUtil.randomString(30) + timestampStr; ``` --- #### 方法三:使用 `ObjectId`(分布式场景) **原理**:Hutool 的 `ObjectId` 包含时间戳、机器标识和计数器,适用于分布式系统[^2]。 **示例代码**: ```java import cn.hutool.core.lang.ObjectId; String objectId = ObjectId.next(); ``` --- ### 关键注意事项 1. **唯一性保证**: - NanoID 和 ObjectId 的设计已大幅降低碰撞概率,适用于大多数场景。 - 若需绝对唯一性,需结合数据库唯一约束或分布式 ID 生成器(如雪花算法)。 2. **性能优化**: - 高频生成时优先使用 `NanoId`,其性能优于 UUID。 3. **字符集控制**: - 可通过参数指定字符范围(如仅数字+字母): ```java String nanoId = NanoId.randomNanoId(RandomUtil.BASE_CHAR_NUMBER.toCharArray(), 16); ``` ---
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值