在范围内生成一个随机数?
可能重复:
在Objective-C中生成随机数
如何生成一个范围内的随机数字?
这实际上比大多数人意识到的要难得多:
int rand_lim(int limit) { /* return a random number between 0 and limit inclusive. */ int divisor = RAND_MAX/(limit+1); int retval; do { retval = rand() / divisor; } while (retval > limit); return retval; }
试图使用%
(或等价地, /
)来获取范围内的数字几乎不可避免地会引入偏斜(即,一些数字将比其他数字更频繁地生成)。
至于为什么使用%
产生偏斜的结果:除非你想要的范围是RAND_MAX的除数,偏斜是不可避免的。 如果你从小数字开始,很容易看出原因。 考虑拿10块糖果,并试图在三个孩子之间均匀分配。 显然这是不可能完成的 – 如果你把所有的糖果都交出来,最近可以得到两个孩子拿到三块糖,其中一块拿到四块。
只有一种方法让所有的孩子都得到相同数量的糖果:确保你根本没有把最后一块糖果分发出去。
为了把这个与上面的代码联系起来,让我们从1到10的糖果和1到3的孩子开始。最初的分组说,因为有三个孩子,我们的除数是三。 然后,我们从桶中随机取出一个糖果,看看它的数量,然后除以三,然后把它交给那个孩子 – 但是如果结果大于3(即我们挑出的糖果数量为10),我们就不会把它拿出来 – 我们丢弃它,挑出另一个糖果。
当然,如果您使用的是C ++的现代化实现(即支持C ++ 11或更新版本),则通常应该使用标准库中的一个distribution
类。 上面的代码与std::uniform_int_distribution
最为接近,但是标准库也包含了uniform_real_distribution
以及一些非均匀分布的类(伯努利,泊松,普通,也许是我现在不记得的其他几个类)。
int rand_range(int min_n, int max_n) { return rand() % (max_n - min_n + 1) + min_n; }
对于分数:
double rand_range(double min_n, double max_n) { return (double)rand()/RAND_MAX * (max_n - min_n) + min_n; }
http://www.cprogramming.com/tutorial/random.html
第二个例子展示了如何通过范围生成
对于[min,max]范围内的整数值:
double scale = (double) (max - min) / RAND_MAX; int val = min + floor(rand() * scale)
我在Obj-C为iPhone项目专门写了这个:
- (int) intInRangeMinimum:(int)min andMaximum:(int)max { if (min > max) { return -1; } int adjustedMax = (max + 1) - min; // arc4random returns within the set {min, (max - 1)} int random = arc4random() % adjustedMax; int result = random + min; return result; }
使用:
int newNumber = [aClass intInRangeMinimum:1 andMaximum:100];
加盐调味
+(NSInteger)randomNumberWithMin:(NSInteger)min WithMax:(NSInteger)max { if (min>max) { int tempMax=max; max=min; min=tempMax; } int randomy=arc4random() % (max-min+1); randomy=randomy+min; return randomy; }
我在一个随机数相关的类中使用这个方法。 适合我的非苛刻的需求,但可能会有一定的偏见。