mardi 7 mars 2023

Function to change random distribution in Swift?

Does Swift have some built in methods to change the distribution of random numbers? I want to use a linear equation to define the distribution, something like y = k * x + m. When k = 0, all numbers should be equally distributed. When k = 1 the distribution should follow the line, so low x-values would be very rare while high x-values would be common. I played around in Excel and tried different strategies and finally came up with this code, which seems to work - but there must be a neater way to do this in Swift?

As a note: First I did use an array of ClosedRange instead of the tuples-approach, then used .contains. Then I changed it to an array of tuples because my code didn't work as expected. Probably another bug, but I stayed with tuples as the code works now.

import Foundation

/* function to create an array of tuples with upper and lower
 limits based on a linear distribution (y = k * x + m) */
func createDistributions(numbers: ClosedRange<Int>, k: Double) -> [(Double, Double)] {
    var dist = [(Double, Double)]()
    let m: Double = 0.5
    let nVal: Int = numbers.count
    var pStop: Double = 0.0

    for x in numbers {
        let t = (Double(x) + 0.5) / Double(nVal)
        let y = (k * (t - 0.5) + m) * 2.0 / Double(nVal)
        let start = pStop
        let stop = y + start
        
        dist.append((start, stop))
        pStop = stop
    }
    
    return dist
}

// create distributions based on k-value of 1.0
var result = createDistributions(numbers: 0...34, k: 1.0)


// loop ten times, creating a Double random number each time
for _ in 0...9 {
    let ran = Double.random(in: 0...1)
    
    // check in which indexed array the random number belongs to by checking lower and upper limit
    for i in 0..<result.count {
        
        // the random number belongs to the i:th element, print i
        if ran >= result[i].0 && ran <= result[i].1 {
            print(i)
        }
    }
}



Aucun commentaire:

Enregistrer un commentaire