【问题标题】:Random permutation of integers using a random number generator使用随机数生成器对整数进行随机排列
【发布时间】:2012-06-03 16:46:57
【问题描述】:

这是我的家庭作业:

Random r = new Random();
public int get100RandomNumber() {
    return 1 + r.nextInt(100);
}

给你一个名为 getrand100() 的预定义函数(上图),它 返回一个整数,它是 1-100 中的一个随机数。你可以打电话 此功能随心所欲,但请注意此功能 是相当资源密集型的。您不能使用任何其他随机 发电机。您不能更改getrand100() 的定义。

输出:以随机顺序打印数字 1-20。 (不是 20 个随机数)

我尝试过的..

public class MyClass {

    static Random r = new Random();
    static HashSet<Integer>;

    public static void main(String args[]) {
        myMethod();
        System.out.println(s);
    }    

    public static void myMethod() {
        boolean b = false;
        s = new HashSet<Integer>();
        int i = getRand100();
        if (i >= 20)
            i = i % 20;
        int j = 0;

        int k, l;
        while (s.size() <= 20) 
        {
            System.out.println("occurence no" + ++j);
            System.out.println("occurence value" + i);
            b = s.add(i);
            while (!b) {
                k = ++i;
                if(k<=20)
                    b = s.add(k);
                if(b==true)
                    break;
                if (!b) {
                    l = --i;
                    if(i>=1&&i<=20)
                        b = s.add(l);
                    if(b==true)
                        break;
                }
            }
        }
        System.out.println(s);
    }

    public static int getRand100()
    {
        return r.nextInt(100) + 1;
    }
}

感谢您的帮助!

【问题讨论】:

  • 你的意思是,如果你得到一个 x == 0 或 x > 20 的数字 x,你必须拒绝它?
  • 我认为“以随机顺序打印 1-20 的数字”是指您想要取出所有 1-20 的数字并以随机顺序打印出来,所有可能的顺序均等可能.对吗?
  • 如果这个问题这么简单,那我就不在这里问了..
  • 删除我的反对票,因为您更新了问题。最好描述一下您使用当前代码获得的结果,以及为什么与您的预期不同。

标签: java algorithm random permutation


【解决方案1】:

我相信您在问如何使用随机数生成器以随机顺序打印出数字 1 到 20。这也称为“随机排列”。 Fischer-Yates shuffle就是这样一种算法。

但是,要实现该算法,您首先需要一个随机数生成器,该生成器可以从 N 个项目中以相等的概率挑选一个,其中 N 的范围从 2 到要洗牌的集合的大小,而您只有一个可以从 100 个项目中以相同的概率选择一个。这可以通过模算术和“重滚”的组合轻松获得。

【讨论】:

  • 也许他只需要一个值从 1 到 20 的数组,然后使用他拥有的随机函数应用 Fishcer-Yates 洗牌算法。为了利用这个 shuffle 函数的时间,数组可以有 101 个元素,从 1 到 20(我猜)。
【解决方案2】:

假设您被允许使用 ArrayList 类,我建议您在列表中填写您想要的数字(在本例中为 1 到 20),然后从列表中随机选择并删除它们。使用getRand100() % theList.size() 对于您的原因应该是足够随机的,您只需要调用它 19 次。当只剩下一个元素时,不再需要从列表中“随机”选择它。 ;-)

【讨论】:

  • 我认为这可能与@Weeble 在另一个答案中建议的 Fisher-Yates shuffle 相同。从来不知道这实际上有一个“官方”名称,因为我很久以前就自己想出了它并且从来没有费心去查找它,因为我发现它“太明显了”。
【解决方案3】:

我相信我已经想出了一种方法来转换 1 和 n 之间的任何数字! (假设项目数已知)到 n 个项目的唯一排列。

本质上,这允许“立即”随机化整个牌组,而无需使用任何洗牌算法。目前,它在 O(n^2) 中运行并且需要使用 BigInteger 包(即在 Java 或 Javascript 中),但我正在寻找优化运行时的方法(尽管老实说,现在 2500 次迭代无论如何都不算​​什么)。无论如何,当给定至少 226 位有效的随机数据时,该函数能够在 10 毫秒内生成一个由 52 个整数组成的混洗数组。

该方法类似于将十进制数转换为二进制数(连续除以 2 等)的方法。我很乐意应要求提供我的代码;我觉得有趣的是我以前没有遇到过。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2015-03-14
    • 2018-10-09
    • 2014-08-22
    • 2020-07-25
    • 1970-01-01
    • 1970-01-01
    • 2023-01-03
    相关资源
    最近更新 更多