Як отримати випадкове значення з масиву?


123

У мене є масив, який називається $ran = array(1,2,3,4);

Мені потрібно дістати випадкове значення з цього масиву і зберегти його в змінній. Як це зробити?

Відповіді:


232

Ви також можете зробити лише:

$k = array_rand($array);
$v = $array[$k];

Це спосіб зробити це, коли у вас є асоціативний масив.


11
відповідно до цього коментаря array_rand не так випадково, як це має бути
Тимо Хуовінен

1
Або ви можете вимагати цей пакет і використовуватиarray_rand_value
мурез

10
Починаючи з PHP 7.1, array_rand()використовується генератор Mersenne Twister: rand (), псевдонім mt_rand () та srand (), псевдонім mt_srand () . На практиці це повинно бути зараз досить добре.
Гра "Двомісний"


23

Ви можете використовувати mt_rand ()

$random = $ran[mt_rand(0, count($ran) - 1)];

Це стане в нагоді і як функція, якщо вам потрібно значення

function random_value($array, $default=null)
{
    $k = mt_rand(0, count($array) - 1);
    return isset($array[$k])? $array[$k]: $default;
}

4
Має бути mt_rand (0, 3), оскільки є лише 4 елементи. Однак правильніше: $ array [mt_rand (0, count ($ array)])
reko_t

2
Помилка, я думаю, ви мали на увазі mt_rand (0, кол. ($ Побіг) - 1)
Джош Девіс

згідно з коментарями php array_rand, не так випадково, як слід, тому mt_randбажано
Тимо Хуовінен

1
Який сенс у всій issetчастині? Це все одно не вдасться для асоціативних масивів.
Люк Двоюрідний

я не знаю чому, але при використанні mt_randзамість randцього випадку здається, що деякі елементи віддають перевагу більше, ніж інші
user151496


14

Ви можете використовувати функцію array_rand для вибору випадкового ключа з масиву, як показано нижче.

$array = array("one", "two", "three", "four", "five", "six");
echo $array[array_rand($array, 1)];

або ви можете використовувати функції rand і підрахунок, щоб вибрати випадковий індекс.

$array = array("one", "two", "three", "four", "five", "six");
echo $array[rand(0, count($array) - 1)];

11

Отримано від Laravel Collection::random():

function array_random($array, $amount = 1)
{
    $keys = array_rand($array, $amount);

    if ($amount == 1) {
        return $array[$keys];
    }

    $results = [];
    foreach ($keys as $key) {
        $results[] = $array[$key];
    }

    return $results;
}

Використання:

$items = ['foo', 'bar', 'baz', 'lorem'=>'ipsum'];

array_random($items); // 'bar'
array_random($items, 2); // ['foo', 'ipsum']

Кілька приміток:

  • $amountмає бути меншим або рівним count($array).
  • array_rand()не перетасовує клавіші (з PHP 5.2.10, див. 48224 ), тому вибрані вами елементи завжди будуть у вихідному порядку. Використовуйте shuffle()після цього, якщо потрібно.


Документація: array_rand(),shuffle()


редагувати: з того часу функція Laravel помітно зросла, див. Laravel 5.4's Arr::random(). Ось щось більш досконале, отримане від функції дорослого Laravel:

function array_random($array, $number = null)
{
    $requested = ($number === null) ? 1 : $number;
    $count = count($array);

    if ($requested > $count) {
        throw new \RangeException(
            "You requested {$requested} items, but there are only {$count} items available."
        );
    }

    if ($number === null) {
        return $array[array_rand($array)];
    }

    if ((int) $number === 0) {
        return [];
    }

    $keys = (array) array_rand($array, $number);

    $results = [];
    foreach ($keys as $key) {
        $results[] = $array[$key];
    }

    return $results;
}

Кілька важливих моментів:

  • Викиньте виняток, якщо недоступних предметів
  • array_random($array, 1)повертає масив одного елемента ( # 19826 )
  • Значення підтримки "0" для кількості елементів ( # 20439 )

8

array_randФункція , здається, має нерівномірний розподіл на великих масивах, не кожен елемент масиву з однаковою ймовірністю отримати взяв. Використання перетасування в масиві та взяття першого елемента не має такої проблеми:

$myArray = array(1, 2, 3, 4, 5);

// Random shuffle
shuffle($myArray);

// First element is random now
$randomValue = $myArray[0];

Це дуже багато додаткової обчислювальної роботи, щоб отримати єдиний випадковий елемент. Інші відповіді, які використовуються mt_rand(), ймовірно, краще підходять до завдання.
rinogo

Я думаю, залежить від ваших потреб. У моєму випадку розподіл був дуже важливим, а обчислювальні витрати не були.
Ассіома

5

Інший підхід через гортаючи масив, щоб отримати пряме значення.

Знімок

$array = [ 'Name1' => 'John', 'Name2' => 'Jane', 'Name3' => 'Jonny' ];
$val = array_rand(array_flip($array));

array_randключ повернення не значення. Отже, ми гортаємо значення як ключове.

Примітка: ключ PHP завжди є унікальним ключем, тому при переверненні масиву повторне значення як ключ буде перезаписано.


Чому б просто не зробити $array[array_rand($array)];?
rinogo

@rinogo Це теж працює, На це вже відповів вище. Це трохи відрізняється від вашої відповіді, array_flipвидаліть дублікат як ключ, а потім дайте результат ... Майте на увазі не дублікат!
Smartpal

4
$rand = rand(1,4);

або, зокрема, для масивів:

$array = array('a value', 'another value', 'just some value', 'not some value');
$rand = $array[ rand(0, count($array)-1) ];

2
Ви ніколи не отримаєте перший елемент у цьому списку, і ви виходите за межі масиву з 4
Ólafur Waage

Перший $ rand - це значення. Оригінальний масив має значення від 1 до 4. Другий $ rand - це клавіші масиву, від 0 до 3.
Джош Девіс

3

У моєму випадку я повинен отримати 2 значення, що таке об’єкти. Я поділяю це просте рішення.

$ran = array("a","b","c","d");
$ranval = array_map(function($i) use($ran){return $ran[$i];},array_rand($ran,2));

2

Чи має ваш вибір якісь наслідки для безпеки? Якщо так, використовуйте random_int()і array_keys(). ( random_bytes()є лише PHP 7, але є PHP 5 ).

function random_index(array $source)
{
    $max = count($source) - 1;
    $r = random_int(0, $max);
    $k = array_keys($source);
    return $k[$r];
}

Використання:

$array = [
    'apple' =>   1234,
    'boy'   =>   2345,
    'cat'   =>   3456,
    'dog'   =>   4567,
    'echo'  =>   5678,
    'fortune' => 6789
];
$i = random_index($array);
var_dump([$i, $array[$i]]);

Демо: https://3v4l.org/1joB1


2

Використовуйте rand (), щоб отримати випадкове число для відлуння випадкового ключа. Наприклад: 0 - 3

$ran = array(1,2,3,4);
echo $ran[rand(0,3)];


2

Мені потрібна була одна версія рядка для короткого масиву:

($array = [1, 2, 3, 4])[mt_rand(0, count($array) - 1)]

або якщо масив виправлений:

[1, 2, 3, 4][mt_rand(0, 3]

2

On-line:

echo $array[array_rand($array,1)]

Хоча цей код може відповісти на питання, надаючи додатковий контекст стосовно того, чому та / або як цей код відповідає на питання, покращує його довгострокове значення.
β.εηοιτ.βε

1

Це буде добре працювати з рядковими масивами. Плюс до того, я думаю, що речі є більш охайними та багаторазовими для використання, коли вони завершені у функції.

function array_rand_value($a) {
    return $a[array_rand($a)];
}

Використання:

array_rand_value(array("a", "b", "c", "d"));

У PHP <7.1.0, array_rand()використовує rand(), тому ви не хочете використовувати цю функцію для нічого, що стосується безпеки чи криптографії. У програмі PHP 7.1.0+ користуйтеся цією функцією без побоювання, оскільки rand()вона була відчуженаmt_rand() .


0

Я базую свою відповідь на функції @ ÓlafurWaage. Я намагався його використати, але стикався з еталонними проблемами, коли я намагався змінити об'єкт повернення. Я оновив його функцію для передачі та повернення за посиланням. Нова функція:

function &random_value(&$array, $default=null)
{
    $k = mt_rand(0, count($array) - 1);
    if (isset($array[$k])) {
        return $array[$k];
    } else {
        return $default;
    }
}

Для отримання додаткового контексту, перегляньте моє запитання в розділі Передача / повернення посилань на об'єкт + зміна об'єкта не працює


0

Простий спосіб отримати значення масиву Randdom з масиву .

$color_array =["red","green","blue","light_orange"];
$color_array[rand(0,3)

тепер кожен раз ви отримуватимете різні кольори від Array .


-5

Ви отримуєте випадкове число з масиву таким чином:

$randomValue = $rand[array_rand($rand,1)];

4
array_rand () повертає випадковий ключ, а не випадкове значення.
reko_t
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.