But what if we need to implement more advanced requirements for generating random numbers. Let's explore possible situations where we generating random numbers and using it.
Generate Random Integer with Upper Bound
For generating random integer in range between 0 and upper bound we use function
rc4random_uniform(N)
This function will return random integer number in the range of 0 to N - 1. So, for example, if N = 42 then maximum number that can be generate will be 41 and minimum will be 0.
rc4random_uniform(42)
This function takes one parameter of type UInt32 and returns value of type UInt32
func arc4random_uniform(_ __upper_bound: UInt32) -> UInt32
So, if you work with values of type Int you have to convert values to type UInt32 when parameter passed to function and convert back to Int when getting result.
let number: Int
number = Int(arc4random_uniform(42))
let inputNumer: Int = 100
let outputNumber: Int
outputNumber = Int(arc4random_uniform(UInt32(inputNumer)))
It is not very handy always do this conversion when generating random numbers. Let's make a function for this:
func random(n: Int) -> Int {
return Int(arc4random_uniform(UInt32(n)))
}
let n: Int
n = random(n: 99)
This function takes one parameter of type Int and return result in range between 0 and N-1 of type Int.
To make it more useful we can create extension for type Int and generating of random integers will be availbale everywhere in code. We also can check for sign before passed parameter because UInt32 type is unsigned type and in case of negative value passed we need to get absolute value from input passed parameter. This method is static and will be available for whole Int type, there is no need to create instance of Int type.
extension Int {
static func random(_ n: Int) -> Int {
if n < 0 {
return -Int(arc4random_uniform(UInt32(abs(n))))
} else if n > 0 {
return Int(arc4random_uniform(UInt32(n)))
} else {
return 0
}
}
}
Int.random(-100) // return in range between -99 and 0
But we can create also an instance method in extension. In this case instance of Int type will be used as upper bound for random number generation function.
extension Int {
func random() -> Int {
if n < 0 {
return -Int(arc4random_uniform(UInt32(abs(self))))
} else if n > 0 {
return Int(arc4random_uniform(UInt32(self)))
} else {
return 0
}
}
}
65.random()
Generate Random Integer in Range (with Lower and Upper Bounds)
What if you need to get random number in special range, for example, between 15 and 25, or between 90 and 100, and etc. So, for that purpose we will write special function.
func randomInRange(lowerBound: Int, upperBound: Int) -> Int {
guard lowerBound < upperBound else {
return lowerBound
}
return lowerBound + Int(arc4random_uniform(UInt32(upperBound - lowerBound + 1)))
}
randomInRange(lowerBound: 20, upperBound: 30)
This function will return random value in range between lowerBound and upperBound, both bounds are inclusive.
We also can use range as parameter, for example, like this 0..<100
func randomInRange(_ range: Range<Int>) -> Int {
guard range.lowerBound < range.upperBound else {
return range.lowerBound
}
return range.lowerBound + Int(arc4random_uniform(UInt32(range.upperBound - range.lowerBound + 1)))
}
randomInRange(0..<100) // will return in range between 0 and 99 inclusive
Range can be closed, for example, like this 0...100, for this we need to change type Range for ClosedRange
func randomInRange(_ range: ClosedRange<Int>) -> Int {
guard range.lowerBound < range.upperBound else {
return range.lowerBound
}
return range.lowerBound + Int(arc4random_uniform(UInt32(range.upperBound - range.lowerBound + 1)))
}
randomInRange(0...100) // will return in range between 0 and 100 inclusive
Now, we can go further and create extension for range. And even more, this extension will work as with normal ranges as with negative ranges.
extension Range where Bound == Int {
var random: Int {
var offset = 0
if lowerBound < 0 {
offset = abs(lowerBound)
}
let lower = UInt32(lowerBound + offset)
let upper = UInt32(upperBound + offset)
return Int(lower + arc4random_uniform(upper - lower + 1)) - offset
}
}
(0..<123).random
(-500..<500).random
Generate Array of Random Numbers
We can create an array of random integer numbers by generating random numbers in for loop.
func generateArrayOfNumbers(count: Int, upperBound: Int) -> [Int] {
var result = [Int]()
for _ in 0..<count {
result.append(Int.random(upperBound))
}
return result
}
generateArrayOfNumbers(count: 10, upperBound: 100)
For generating random numbers we can use, for example, extension for range that we wrote above.
func generateArrayOfNumbers(count: Int, range: Range<Int>) -> [Int] {
var result = [Int]()
for _ in 0..<count {
result.append(range.random)
}
return result
}
generateArrayOfNumbers(count: 10, range: 0..<10)
One Line Generation
For generating array we can use map function for ranges. Every element of range will be used as iteration in a loop and random number will be generated and added to array.
For closed range
var randomArray = (1...10).map { _ in Int(arc4random_uniform(100)) }
Or for non-closed range
var randomArray = (1..<10).map { _ in Int(arc4random_uniform(100)) }
Generate Array of Unique(Non Repeating) Random Numbers
In case we need generate array of random numbers without repeating values we can use following strategies:
1. Using contains method of Array and repeat while loop
func uniqueRandomArray(count: Int, min: Int, max: Int) -> [Int] {
guard count <= (max - min + 1) else {
return []
}
var numbers = [Int]()
for i in 1...count {
var random: Int
repeat {
random = min + Int(arc4random_uniform(UInt32(max - min + 1)))
} while numbers.contains(random)
numbers.append(random)
}
return numbers
}
var randomArray = uniqueRandomArray(count: 10, min: 15, max: 55)
2. Using Set<Int> and while loop
func uniqueRandomArray(count: Int, min: Int, max: Int) -> [Int] {
guard count <= (max - min + 1) else {
return []
}
var numbers = Set<Int>()
while numbers.count < count {
let random = min + Int(arc4random_uniform(UInt32(max - min + 1)))
numbers.insert(random)
}
return Array(numbers)
}
var randomArray = uniqueRandomArray(count: 50, min: 11, max: 99)
3. Using additional Array with numbers
func uniqueRandomArray(count: Int, min: Int, max: Int) -> [Int] {
guard count <= (max - min + 1) else {
return []
}
var numbers = Array(min...max)
var randoms = [Int]()
for _ in 1...count {
let index = Int(arc4random_uniform(UInt32(numbers.count)))
let value = numbers[index]
randoms.append(value)
numbers.remove(at: index)
}
return randoms
}
var randomArray = uniqueRandomArray(count: 10, min: 1, max: 10)
Get Random Element From Array
For getting random item from array you need just generate random index and get item with this index.
let array = ["Star", "Wars", "Empire", "Strikes", "Back"]
let randomIndex = Int(arc4random_uniform(UInt32(array.count)))
print(array[randomIndex])
Generate Random UIColor
For generating random UIColor lets explore one of initializer that available for class UIColor.
UIColor(red: CGFloat, green: CGFloat, blue: CGFloat, alpha: CGFloat)
As we can see there are float components, so we can randomly generate integer numbers and convert these values to CGFloat.
let redComponent = CGFloat(arc4random_uniform(255)) / 255.0
let greenComponent = CGFloat(arc4random_uniform(255)) / 255.0
let blueComponent = CGFloat(arc4random_uniform(255)) / 255.0
let randomColor = UIColor(red: redComponent, green: greenComponent,
blue: blueComponent, alpha: 1.0)
Function for creating random color
func randomColor(randomAlpha: Bool = false) -> UIColor {
let redComponent = CGFloat(arc4random_uniform(255)) / 255.0
let greenComponent = CGFloat(arc4random_uniform(255)) / 255.0
let blueComponent = CGFloat(arc4random_uniform(255)) / 255.0
let alphaComponent = randomAlpha ? CGFloat(arc4random_uniform(255)) / 255.0 : 1
let randomColor = UIColor(red: redComponent, green: greenComponent,
blue: blueComponent, alpha: alphaComponent)
return randomColor
}
let randomColor2 = randomColor(randomAlpha: false)
Making an extension for UIColor
extension UIColor {
class func random(randomAlpha: Bool = false) -> UIColor {
let redComponent = CGFloat(arc4random_uniform(255)) / 255.0
let greenComponent = CGFloat(arc4random_uniform(255)) / 255.0
let blueComponent = CGFloat(arc4random_uniform(255)) / 255.0
let alphaComponent = randomAlpha ? CGFloat(arc4random_uniform(255)) / 255.0 : 1
let randomColor = UIColor(red: redComponent, green: greenComponent,
blue: blueComponent, alpha: alphaComponent)
return randomColor
}
}
UIColor.random()
Source Code
Source code for this post could be found here on
GitHub
Really nice article. its really helpful me. Very interesting and good post thanks for sharing such a good blog.
ReplyDelete-Web Development Services
There are many articles circulating on internet that exaggerate about Custom Designed Websites. But your article is an exception that made me understand it without any difficulty.
ReplyDeleteThank you very much for bringing this to my attention. Your blog is chock-full of useful information. I'd have no idea unless I read that. I'll return for more excellent content. Best wishes and best of success to you. Best Custom Websites
ReplyDeleteGreat content. I was looking for this kind of content. It saved my time to search further.
ReplyDeleteYou must provide such type of content constantly. I appreciate your willingness to provide readers with a good article.
Custom Design Websites
Thank you for writing this quality informational content.Your writing technique is impressive and enjoyable to read. I'll come back for more fantastic material.
ReplyDeleteBest wishes, and good luck.
Custom Build Website
Thanks to your article now I understand or learn many new things which are very difficult to understand the way you describe this topic is very easy to understand. Web Design USA
ReplyDeleteThank you for writing this quality informational content. Your writing technique is good and enjoyable to read. I'll come back for more fantastic material.
ReplyDeleteBest wishes, and good luck.
Mobile Performance Meter Hack
Great share!One of the best blogs I have Ever Seen. Keep going!
ReplyDeleteSEO Service NYC
I adore your work, and it greatly motivates me.
ReplyDeleteMobile App Testing Services
This is one of the nicest blogs I've ever seen, and it's really
ReplyDeletepleasant. This is a very valuable blog for me, and one of the most
helpful blogs I've ever seen.
Search Engine Marketing Services
One of the best blogs I have ever seen. Keep going!
ReplyDeletePaul allen | CBD Crystal Isolate Wholesale
Please keep writing this type of article posts; I like it.
ReplyDeleteAmber Cooper | Pure CBD Disposable