Я в основном ищу эквивалент Elixir Ruby Array#sample
. Что-то, что позволит мне сделать это:
list = [1,2,3,4,5,6,7]
sample(list)
#=> 4
sample(list, 3)
#=> [6, 2, 5]
Я ничего не нашел в Документах по спискам эликсиров.
Я в основном ищу эквивалент Elixir Ruby Array#sample
. Что-то, что позволит мне сделать это:
list = [1,2,3,4,5,6,7]
sample(list)
#=> 4
sample(list, 3)
#=> [6, 2, 5]
Я ничего не нашел в Документах по спискам эликсиров.
Как сказал Хосе Валим в своем ответе, в Elixir 1.1
и выше вы можете использовать эти методы для получения случайных элементов из списка:
Enum.random/1
- для получения одного случайного элементаEnum.take_random/2
- для получения нескольких случайных элементовПример:
Enum.random(list) #=> 4
Enum.take_random(list, 3) #=> [3, 9, 1]
Enum.take_random(list, 1) #=> [7]
Не забудьте :random.seed(:erlang.now)
вызвать :random.seed(:erlang.now)
!
Я все еще не могу найти "правильный" и "магический" способ сделать это, но это лучшее, что я мог бы придумать:
Для получения одного случайного элемента:
list |> Enum.shuffle |> hd
#=> 4
Примечание. Это дает исключение, если list
пуст
Для получения нескольких случайных элементов:
list |> Enum.shuffle |> Enum.take(3)
#=> [7, 1, 5]
В Elixir 1.0 такой функции нет, поэтому вам нужно реализовать ее самостоятельно, как упомянуто другими решениями. Однако Enum.random/1
идет с Elixir v1.1: https://hexdocs.pm/elixir/Enum.html#random/1
Другой способ (для выборки только одного элемента):
list |> Enum.at(:random.uniform(length(list)) - 1)
Возможно, предпочтительнее другого метода, если вы работаете с достаточно большими списками, которые могут повлиять на перетасовку всего списка.
комментарий Gazler об использовании :random.seed(:erlang.now)
по-прежнему применяется.
Если вы используете более новую версию Elixir, там есть функция Enum.take_random/2
, добавленная в Elixir v1.1.
От Elixir v1.1 документация:
Принимает случайные элементы из коллекции.
Обратите внимание, что эта функция пересечет всю коллекцию, чтобы получить случайный подсписк коллекции. Если вам требуется случайное число между двумя целыми числами, лучшим вариантом является использование: случайного модуля.
Итак, отвечая на вопрос, взятие нескольких элементов из списка будет выглядеть так:
list = [1,2,3,4,5,6,7]
Enum.take_random(list, 3)
#=> [2, 4, 1]
Или, для одного элемента:
list = [1,2,3,4,5,6,7]
Enum.take_random(list, 1)
#=> [1]