/** * implement some useful random-function */ /** * generates a random integer in [{@param inclusiveMin}; {@param exclusiveMax}). * * @param inclusiveMin {number} * @param exclusiveMax {number} * * @return {number} a random integer in [{@param inclusiveMin}; {@param exclusiveMax}). * */ export function uniform(inclusiveMin= 0, exclusiveMax) { let a = inclusiveMin, b = exclusiveMax; if (arguments.length === 1) { // only the first is set => there is no left bound a = 0; b = inclusiveMin; } if ( (b <= a) || (b-a) >= Number.MAX_VALUE ) { throw Error(`bad range [${a}, ${b})`) } return a + (Math.floor( (b-a)*Math.random() )); } /** * generates a random discrete distribution of a given probability of distribution * For example: given a probability of `[0.1, 0.3, 0.6]`, then the random generate number ist * one of 0 (with probability of 1%) , 1 (30%) and 2(60%). * * @param distribution {Array} an array of number, sum of its element must be at most 1 * @return {number} an integer between 0 (include) and {@param distribution.length} (exclude) * * */ export function discrete(distribution) { let sum = distribution.reduce( (acc,current) => acc + current); let dist = undefined; if(sum > 1) { throw Error(`bad distribution [${distribution}]`); } else if (sum < 1) { dist = [...distribution, 1 - sum]; } else { dist = [...distribution]; } let r = Math.random(); let i = 0; let acc = dist[0]; while(r >=acc ) { ++i; acc += dist[i]; } return i; }