【问题标题】:How to choose between two values in a random way?如何以随机方式在两个值之间进行选择?
【发布时间】:2020-05-17 23:16:11
【问题描述】:

我正在尝试随机选择两个数字之一:2-2。有没有办法做到这一点?我正在尝试实现一种算法来创建迷宫。

【问题讨论】:

标签: c random numbers


【解决方案1】:

您有来自 C 标准库的 rand(),它返回 [0, RAND_MAX] 范围内的伪随机整数。您可以使用此函数并选择两个数字之一来检查返回的值是高于还是低于RAND_MAX/2

首先,使用srand() 用一些种子初始化伪随机数生成器。通常使用time() 来执行此操作,因为它每次都返回不同的值。

srand(time(NULL));

int rnd = rand();
int result = (rnd > RAND_MAX/2) ? 2 : -2;

或者,您可以使用rand() 返回的值的最低有效位,正如this other answer 中所建议的那样,因为返回的值的一半是奇数,一半是偶数:

int result = (rnd & 1) ? 2 : -2;

【讨论】:

    【解决方案2】:

    有很多方法可以做到这一点,我最喜欢的是:

    a + rand() % 2 * (b - a);
    

    但它不清楚它做了什么并且它对效率没有贡献(如果你将它变成一个宏/内联函数并且从未与变量一起使用,现代编译器应在编译时评估数字),因此最优雅的方法是使用某种条件,这是一个使用三元运算符的示例:

    (rand() % 2)? a: b;
    

    顺便说一句:有很多方法可以在 0/1 之间进行选择,我使用 rand()%2 因为它是最常用的技术, 但是,如果您碰巧在没有模/除法的 6502 架构上执行此操作,您可以使用像 rand() & ANY_POWER_OF_TWO 或像这样 rand() > 这样的按位与运算符来执行此操作HALF_MAX_RAND

    【讨论】:

      【解决方案3】:

      你可以使用它。它使用按位运算来生成2-2 而无需分支:

      -((rand() & 1) << 2) + 2
      

      我注意到您应该在使用之前使用srand() 为随机数生成器播种;我常用srand(time(NULL))

      一步一步:

      • (rand() &amp; 1) 生成一个随机数:01

      • &lt;&lt; 2 将前面的结果乘以4,而-((rand() &amp; 1) &lt;&lt; 2) 前面的- 否定了这一点,所以结果要么是0 要么是-4

      • + 2 加上2,所以结果是2-2

      如果您想看到一种更类似于算术的方法,可能更容易理解,这里是:

      rand % 2 * -4 + 2
      

      【讨论】:

        猜你喜欢
        • 2019-08-19
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2013-02-23
        • 2012-05-19
        • 1970-01-01
        • 2012-05-19
        • 1970-01-01
        相关资源
        最近更新 更多