An array of random numbers with a range of values of a certain amount of php
The task is to create an array of random numbers of a certain length, with a given range of numbers, so that the sum has a certain value. For example, you need 5 numbers, with a range of 5-20, for a total of 50. The output needs something like 6, 12, 13, 8, 11.
For those who will be looking for a solution to such a problem, so far the only one (you can immediately pick it up for yourself):
function array_rand_with_sum($min, $max, $sum, $num)
{
$a = array();
if ($max*$num > $sum && $min < $sum\$num)
{
do
{
for($i = 0; $i < $num; $i ++)
{
$a[$i] = mt_rand($min, $max);
}
}
while(array_sum($a) != $sum);
return $a;
}
else { return "Ошибка! Проверьте входные данные."; }
}
If someone finds a better one, I will be very happy!
4
Author: Nick Volynkin, 2015-05-13
2 answers
To hope that your function will terminate rather recklessly, try these input parameters:
array_rand_with_sum(1, 1000, 10000, 200);
I have never managed to get a result out of a dozen attempts.
My version of the function is something like this:
function array_rand_with_sum($min, $max, $sum, $num)
{
if ($num <= 0 || $max * $num < $sum || $min * $num > $sum) {
return "Ошибка! Проверьте входные данные.";
}
if ($num == 1) {
return [$sum];
}
$rand = mt_rand(
max($min, $sum - $max * ($num - 1)),
min($max, $sum - $min * ($num - 1))
);
$res = array_rand_with_sum($min, $max, $sum - $rand, $num - 1);
$res[] = $rand;
return $res;
}
$res = array_rand_with_sum(1, 1000, 10000, 200);
if (is_array($res)) {
var_dump([
'min' => min($res),
'max' => max($res),
'sum' => array_sum($res),
'count' => count($res),
]);
}
var_dump($res);
2
Author: actofgod, 2015-05-14 09:57:33
Not pretty, but as an option
function array_rand_with_sum($min, $max, $sum, $num)
{
$return = array();
$newsum = $sum;
for($i=0;$i<$num;$i++) {
$c = rand($min,($max<$newsum)?$max:$newsum);
$newsum -= $c;
$return[]= $c;
}
$array_sum = array_sum($return);
arsort($return);
if($array_sum>$sum) {
$return[0]-= ($array_sum-$sum);
} else {
$return[count($return)-1]+= ($sum-$array_sum);
}
return $return;
}
-1
Author: Mike, 2015-05-14 07:31:23