Подтвердить что ты не робот

Каков самый простой способ генерации случайных целых чисел в диапазоне в Swift?

Метод, который я разработал до сих пор, таков:

func randRange (lower : Int , upper : Int) -> Int {
    let difference = upper - lower
    return Int(Float(rand())/Float(RAND_MAX) * Float(difference + 1)) + lower
}

Это генерирует случайные целые числа между нижним и верхним включительно.

4b9b3361

Ответ 1

Здесь несколько более легкая версия:

func randRange (lower: Int , upper: Int) -> Int {
    return lower + Int(arc4random_uniform(UInt32(upper - lower + 1)))
}

Это можно упростить, если вы решите, что эта функция работает только с неподписанными значениями:

func randRange (lower: UInt32 , upper: UInt32) -> UInt32 {
    return lower + arc4random_uniform(upper - lower + 1)
}

Или, следуя за Антоном (+1 для вас) отличной идеей использования диапазона в качестве параметра:

func random(range: Range<UInt32>) -> UInt32 {
    return range.startIndex + arc4random_uniform(range.endIndex - range.startIndex + 1)
}

Ответ 2

Отредактировано для удаления смещения по модулю в соответствии с предложением в комментариях. (Спасибо!)

Я думаю, что аккуратным способом сделать это может быть использование Swift Range для определения границ, потому что тогда вы можете указать 1..100 или 1... 100 (включая или исключая верхнюю границу). Самое лучшее, что я придумал до сих пор:

import Foundation // needed for rand()

func randInRange(range: Range<Int>) -> Int {
    // arc4random_uniform(_: UInt32) returns UInt32, so it needs explicit type conversion to Int
    // note that the random number is unsigned so we don't have to worry that the modulo
    // operation can have a negative output
    return  Int(arc4random_uniform(UInt32(range.endIndex - range.startIndex))) + range.startIndex
}

// generate 10 random numbers between -1000 and 999
for _ in 0...100 {
    randInRange(-1000...1000)
}

Я попытался использовать расширение на Range, но вы не можете увеличить Range < T, где T: Int > конкретно. Было бы даже лучше, если бы вы могли получить синтаксис вроде (1..100).rand().

Ответ 3

Если вы используете расширения:

extension CountableClosedRange where Bound == Int {
    var randomValue: Int {
        return lowerBound + Int(arc4random_uniform(UInt32(upperBound - lowerBound)))
    }
}

extension CountableRange where Bound == Int {
    var randomValue: Int {
        return lowerBound + Int(arc4random_uniform(UInt32(upperBound - lowerBound)))
    }
}

(0...6).randomValue
(0..<7).randomValue