我意识到Swift书籍提供了一个随机数生成器的实现。复制和粘贴这个实现是最佳实践吗?或者有没有这样的库,我们现在就可以使用?


当前回答

对于0到n-1之间的随机整数,使用arc4random_uniform(n)。

let diceRoll = Int(arc4random_uniform(6) + 1)

将结果转换为Int,这样你就不必显式地将你的vars类型为UInt32(这看起来不像swifty)。

其他回答

 let MAX : UInt32 = 9
 let MIN : UInt32 = 1

    func randomNumber()
{
    var random_number = Int(arc4random_uniform(MAX) + MIN)
    print ("random = ", random_number);
}

@jstn的回答很好,但有点啰嗦。Swift被称为面向协议的语言,因此我们可以通过为协议扩展添加默认实现,而不必为整数族中的每个类实现样板代码来实现相同的结果。

public extension ExpressibleByIntegerLiteral {
    public static func arc4random() -> Self {
        var r: Self = 0
        arc4random_buf(&r, MemoryLayout<Self>.size)
        return r
    }
}

现在我们可以做:

let i = Int.arc4random()
let j = UInt32.arc4random()

其他的整数类都是可以的。

我已经能够使用rand()来获得一个随机的CInt。你可以使用这样的方法使它成为Int型:

let myVar: Int = Int(rand())

你可以使用你最喜欢的C随机函数,并在需要时将值转换为Int。

你可以像在C中那样做:

let randomNumber = arc4random()

推断randomNumber类型为UInt32(32位无符号整数)

使用arc4random_uniform ()

用法:

arc4random_uniform(someNumber: UInt32) -> UInt32

这将为您提供0到someNumber - 1范围内的随机整数。

UInt32的最大值为4,294,967,295(即2^32 - 1)。

例子:

抛硬币 让flip = arc4random_uniform(2) // 0或1 骰子滚 Let roll = arc4random_uniform(6) + 1 // 1 十月的任意一天 Let day = arc4random_uniform(31) + 1 // 1 90年代的任意一年 Let year = 1990 + arc4random_uniform(10)

一般形式:

let number = min + arc4random_uniform(max - min + 1)

其中number、max、min为UInt32。

是什么……

arc4random ()

你也可以通过使用arc4random()得到一个随机数,它会产生一个在0到2^32-1之间的UInt32。因此,要得到一个介于0和x-1之间的随机数,可以将其除以x并取余数。或者换句话说,使用余数运算符(%):

let number = arc4random() % 5 // 0...4

然而,这会产生轻微的模数偏差(参见这里和这里),所以这就是为什么建议使用arc4random_uniform()。

从Int转换到Int

通常情况下,为了在Int和UInt32之间来回转换,这样做是很好的:

let number: Int = 10
let random = Int(arc4random_uniform(UInt32(number)))

但问题是,Int的范围是-2,147,483,648…2,147,483,647在32位系统和范围-9,223,372,036,854,775,808…9223,372,036,854,775,807在64位系统上。将其与0…4,294,967,295的UInt32范围进行比较。U (UInt32)表示无符号。

考虑以下错误:

UInt32(-1) // negative numbers cause integer overflow error
UInt32(4294967296) // numbers greater than 4,294,967,295 cause integer overflow error

所以你只需要确保你的输入参数是在UInt32范围内,你不需要输出是在这个范围之外。