【问题标题】:How to generate random numbers without repetition如何生成不重复的随机数
【发布时间】:2015-02-17 17:11:25
【问题描述】:

我用这个代码生成一个随机数:

int randomNumber = (int) (Math.random() * 7);

我想停止生成重复的号码,我想在我的应用再次打开后生成一个新号码。

我该怎么办?

【问题讨论】:

  • 在文件/数据库中维护编号并继续更新相同的...
  • 您可以将List 与所有允许的随机数一起使用,然后在生成元素时删除它们
  • 你想完成什么?也许您真正需要的是 GUID?
  • 我不认为int randomNumber = (int) (Math.random() * 7); 足以生成 GUID。

标签: java android


【解决方案1】:

将您生成的数字存储在Set 中。然后每次生成一个新的随机数时,测试它是否已经存在于这个 Set 中。

Set<Integer> nums = new HashSet<Integer>();

// Initialize set on app boot

int rnum;
do {
  rnum = (int) (Math.random() * 7);
} while (!nums.contains(rnum));

// Update the set
nums.add(rnum);

// Use rnum now..

您还需要在应用关闭之前保留 Set 值;在onPause()onStop() 方法中。您可以使用SharedPreferences 或简单地序列化/反序列化Set。使用数据库将是大材小用。

【讨论】:

  • 所以你生成的数字越多,生成下一个数字的尝试次数就越多……
【解决方案2】:

第一步:创建数组

第 2 步:用适当的数字填充数组

第 3 步:随机排列数组。

private Integer[] randomNumbersRange(int numberRange) {
    //Create and shuffle array
    Integer[] randomNumbers = new Integer[numberRange];
    for (int i = 0; i < randomNumbers.length; i++) {
        randomNumbers[i] = 1 + i;
    }
    Collections.shuffle(Arrays.asList(randomNumbers));
    return randomNumbers;
}

【讨论】:

    【解决方案3】:

    要在每个应用打开时产生独特的价值,您可以使用

    System.currentTimeMillis()
    

    这将返回 long 而不是 int

    【讨论】:

    • 这与 OP 的问题有什么关系?
    • 他需要一个独特的值,他从来没有说过要围绕随机数旋转
    • 不,问题是:I want to stop generate dupilcate number and I want to generate a new number after my app opens again.。这似乎与这个答案无关。
    • 所以,这永远不会产生重复的值,而且每次都会产生新的东西
    • 它如何生成一个符合 (0, 7) 范围的数字? int randomNumber = (int) (Math.random() * 7); 每次启动应用程序时都有哪些不同(因此,需要某种持久性)?
    【解决方案4】:

    这是确保没有重复的一种方法;

    public int generateRandomNumber(){
    SharedPreferences sp = PreferenceManager.getDefaultSharedPreferences(this);
    final int lastNumber = sp.getInt("lastNumber", 0);
    int randomNumber = (int) (Math.random() * 7);
    while(randomNumber == lastNumber){
    randomNumber = (int) (Math.random() *7);
    }
    sp.edit().putInt("lastNumber", randomNumber).apply();
    return randomNumber;
    }
    

    编辑:这是一种愚蠢的方式来做你想做的事:

    String _p = sp.getString("previousNumbers", "");
    String[] previousNumbers = _p.split(";");
    int randomNumber = (int) (Math.random() * 7);
    while(Arrays.asList(previousNumbers).contains(Integer.toString(randomNumber))
    {
    randomNumber = (int) (Math.random() * 7);
    }
    _p.concat(Integer.toString(randomNumber) + ";");
    sp.edit().putString("previousNumbers",_p).apply();
    return randomNumber;
    

    【讨论】:

    • 但是这种方法不会在重新启动之间保留生成的数字。 I want to stop generate dupilcate number and I want to generate a new number after my app opens again.
    • @DerGolem 将您生成的号码保存在某个数据库表或本地文件中,并在每次创建号码时更新,并检查之前是否创建过天气。
    • 此外,除了最后一个生成的数字之外,此方法不跟踪历史数字...
    • @Dipen_a 谢谢。但我不想知道答案。因为我没有问这个问题。
    • @Solarnum 但是这次编辑现在只保存最后生成的号码,而不是之前的所有号码。
    【解决方案5】:

    也许检查一下使用系统时间戳或您在应用程序外部(存储/数据库/等)保留的其他值来为您的号码播种。

    https://developer.android.com/reference/java/util/Random.html#setSeed(long)

    【讨论】:

    • 这不是答案,而是建议
    • 是的,这个问题很难直接回答。用户要求在启动时生成“一个”非重复随机数。这听起来像是一个潜在的播种问题,没有更多的数据。
    猜你喜欢
    • 1970-01-01
    • 2017-05-23
    • 2012-06-01
    • 1970-01-01
    • 2012-01-23
    • 1970-01-01
    相关资源
    最近更新 更多