【问题标题】:No repeating random number in loop循环中没有重复的随机数
【发布时间】:2017-05-01 17:08:26
【问题描述】:

我是 Java 初学者,现在,我正在尝试在电脑播放器中创建猜谜游戏。我的 ASL 流利,如果我的英语语法不好,请原谅我。我会尽力说明这一点。

我试图阻止整数中的重复随机数。我使用arraylist从列表中随机生成,似乎随机仍然获取相同的值,我认为随机不会有相同的值。我使用了 Collections.shuffle,但它只适用于数组。我用了arraylist contains,但它要求至少有一个数组才能判断为真或假,开始运行java时数组为空时无法确定真假。 请任何人都可以帮助我阻止这种重复?提前谢谢你。 这个“int a”来自其他类文件(它是一个 Math.random)。

public class GameGuess extends Thread {

    int a;

    public void Send(int a) {

        this.a = a;

        ArrayList myArray = new ArrayList();
        ArrayList secArray = new ArrayList();

        Random rand = new Random();
        int p1;
        int p2;

        do {

            p1 = (rand.nextInt(60 - 50) + 50);
            p2 = (rand.nextInt(60 - 50) + 50);

            myArray.add(p1);
            secArray.add(p2);

            System.out.println("Player 1: " + p1);
            System.out.println("Player 2: " + p2);

            if (p1 == a && p2 == a) {
                System.out.println("Both Player1 and 2 are tied!");
                break;
            }
            if (p1 == a) {
                System.out.println("Player 1 wins!");
            }
            if (p2 == a) {
                System.out.println("Player 2 wins!");
            }
            if (p1 != a && p2 != a) {
                System.out.println("No one win, try again!");
            }

        } while (p1 != a && p2 != a);

        System.out.println("Player 1 picked: " + myArray);
        System.out.println("Player 2 picked: " + secArray);
        System.out.println("The secret number is " + a);

    }
}

【问题讨论】:

  • “我认为随机不会有相同的值” - 随机并不意味着不重复(这已经打破了随机的定义)并且在代码中你总是有 伪-随机数生成器。
  • 在向数组添加数字之前,您可以使用 .contains 查看它是否已经是数组列表,如果是则重新滚动。
  • 也许您可以使用 TreeSet(因此您只有唯一的编号,按排序顺序),并检查 Set 是否包含您生成的编号。如果是,请再试一次。否则,请使用数字。
  • Collections.shuffle,但它只适用于数组:不。 Collections.shuffle() 将 List 作为参数。 docs.oracle.com/javase/8/docs/api/java/util/…。 shuffle() 有什么问题?为什么在 Java 5 发布 12 年后,您仍然使用原始 ArrayLists 而不是通用 ArrayList

标签: java random


【解决方案1】:

使用Set 拒绝已经尝试过的随机猜测。 Set 将比 List 更有效一点,但更重要的是,它会让任何阅读您的代码的人清楚,集合中的每个元素只能出现一次。这使您的代码更加清晰。

Set<Integer> p1Guesses = new LinkedHashSet();
Set<Integer> p2Guesses = new LinkedHashSet();

int p1, p2;
do {
  p1 = rand.nextInt(10) + 50;
  while (!p1Guesses.add(p1))
    p1 = rand.nextInt(10) + 50;
  p2 = rand.nextInt(10) + 50;
  while (!p2Guesses.add(p2))
    p2 = rand.nextInt(10) + 50;
  ...

使用LinkedHashSet,将记录猜测的顺序。 Setadd()方法如果集合中已经存在添加的元素,则返回false,这样条件就可以控制循环了。

或者,您可以将范围内的所有数字添加到列表中,然后shuffle 它。但是如果你想打印已经尝试过的猜测,它会稍微改变逻辑。本质上,您需要在每个洗牌列表中找到a 的索引。以较低者为准。您可以打印从零到其各自正确索引的每个猜测字符串的sub-list

【讨论】:

    【解决方案2】:

    如果玩家已经拥有了,你可以生成一个新的随机数:

        ArrayList myArray = new ArrayList();
        ArrayList secArray = new ArrayList();
    
        Random rand = new Random();
        int p1;
        int p2;
    
        do {
    
            p1 = (rand.nextInt(60 - 50) + 50);
    
            while (myArray.contains(p1))
            {
                p1 = (rand.nextInt(60 - 50) + 50);
            }
    
            p2 = (rand.nextInt(60 - 50) + 50);
    
            while (secArray.contains(p2))
            {
                p2 = (rand.nextInt(60 - 50) + 50);
            }
    
            myArray.add(p1);
            secArray.add(p2);
    

    【讨论】:

    • 哇!有用!太感谢了!!!我非常感谢!!!我向你保证,我会向任何需要帮助的人支付转发费用!
    【解决方案3】:

    您可以升级您的条件,但有迭代限制。例如,

        int maxGame = 100;
        int i = 0;
    
            do {
    
                p1 = (rand.nextInt(60 - 50) + 50);
                p2 = (rand.nextInt(60 - 50) + 50);
    ...
    
               i++;
            } while (i<maxGame && p1 != a && p2 != a);
    

    【讨论】:

      猜你喜欢
      • 2011-03-04
      • 1970-01-01
      • 2013-05-26
      • 1970-01-01
      • 2013-08-16
      • 2016-08-07
      • 2013-05-29
      • 1970-01-01
      相关资源
      最近更新 更多