To wyzwanie jest raczej proste:
otrzymujesz tablicę dodatnich (nie licząc 0) liczb całkowitych i musisz wybrać losowy element z tej tablicy.
Ale oto zwrot akcji:
prawdopodobieństwo wyboru elementu zależy od wartości liczby całkowitej, co oznacza, że wraz ze wzrostem liczby całkowitej rośnie również prawdopodobieństwo jej wyboru!
Przykład
Dostajesz tablicę [4, 1, 5]
.
Prawdopodobieństwo wybrania 4 jest równe 4 podzielone przez sumę wszystkich elementów w tablicy , w tym przypadku 4 / ( 4 + 1 + 5 ) = 4 / 10 =
40%
.
Prawdopodobieństwo wyboru 1 to 1 / 10
lub 10%
.
Wejście
Tablica dodatnich liczb całkowitych.
Wynik
Zwróć wybraną liczbę całkowitą, jeśli używasz metody, lub wydrukuj ją bezpośrednio stdout
.
Zasady
- To jest golf golfowy, więc wygrywa najkrótszy kod w bajtach w dowolnym języku.
- Standardowe luki są zabronione.
code-golf
array-manipulation
random
Ian H.
źródło
źródło
R , 25 bajtów
Wypróbuj online!
Wyjaśnienie:
Pobiera próbkę
s
wielkości1
bez wymiany, z odważnikamis
; są one przeskalowane do prawdopodobieństw.Aby zweryfikować dystrybucję, użyj tego linku .
źródło
Pyth , 4 bajty
Wypróbuj tutaj.
Oszczędność jednego bajtu dzięki @Jakube, z dość nietypowym podejściem.
Pyth , 5 bajtów
Wypróbuj tutaj!
W jaki sposób?
# 1
# 2
źródło
OsmL
lubOsmR
d
, a następnie mapyd
w zakresie ... geniusz!CJam (9 bajtów)
Demo online . Jest to pełny program, który pobiera dane wejściowe w formacie tablicy CJam na standardowe wejście i drukuje wybrany element na standardowe wyjście.
Sekcja
źródło
Perl 6 , 20 bajtów
Oszczędność 1 bajtu dzięki @Brad Gilbert b2gills.
Wypróbuj online!
To wymaga 1 argumentu listy. Spakowujemy 2 kopie tej listy za pomocą
xx
operatora. Tak więc@_ Zxx@_
, otrzymujemy listę, w której elementx
jest prezentowanyx
razy. Następnie jest przymuszany doBag
, która jest kolekcją, która przechowuje obiekty wraz z tym, ile razy pojawiają się w kolekcji. Na koniec wybieramy losowy element z tej kolekcjipick
, który bierze pod uwagę liczby i robi The Right Thing ™.źródło
{bag(@_ Z=>@_).pick}
{bag(@_ Zxx@_).pick}
Python 3.6 , 44 bajty
Yay dla wbudowanych. Drugi
A
wchoices(A, A)
to opcjonalnyweights
argument.Wypróbuj online!
źródło
MATL ,
86 bajtówWypróbuj w MATL Online!
Wyjaśnienie
źródło
Mathematica, 19 bajtów
źródło
Rubinowy , 32 bajty
Wypróbuj online!
źródło
Python 3 , 62 bajty
Wypróbuj online!
źródło
Java (OpenJDK 8) ,
88878683 bajtówWypróbuj online!
źródło
for(r*=Math.random();;)
jest to potrzebne lub czy wszystko, czego potrzebujesz, tor*=Math.random()
.for(;;)
pętli wymagałoby to drugiej (nigdy nie osiągniętej) instrukcji return pofor(int i:a)...
spełnieniu wymagań kompilatora - która byłaby o 3 bajty dłuższa.for(int i:a)
jest jakforeach
w C #. Miałem ten sam problem, ale po prostu użyłemfor
pętli. Twoja nowa odpowiedź intryguje mnie, mogę spróbować przekreślić niektóre z twoich pomysłów.J,
878 bajtów7 bajtów jest nieprawidłowy; Przywrócę to do poprzedniej edycji, gdy wrócę do komputera za dzień lub dwa.
Wypróbuj online!
:( wybranie losowych elementów z tablicy jest kosztowne.
8 bajtów
9 bajtów
Wyjaśnienie
źródło
?@+/
jest(?@+)/
; Obawiam się, że będziesz musiał ponownie podnieść to do 8…JavaScript (ES6), 50 bajtów
Mam nadzieję, że to oczywiste, jak to działa, ale i tak to wyjaśnię. Sortuje liczby całkowite w kolejności malejącej, a następnie wybiera jedną losowo z rozproszeniem beta (1 / 2,1) .
źródło
a=[4,1,5]
, otrzymasz około 18%1
, 24%4
i 58%5
, co sugeruje, że otrzymasz ten rozkład z dowolnym wkładem o długości 3.05AB1E , 9 bajtów
Wypróbuj online!
źródło
PowerShell , 27 bajtów
Wypróbuj online!
Pobiera dane wejściowe
$args[0]
jako tablicę literalną. Pętle przez każdy element|%{...}
, a w każdej iteracji tworzy się nową tablicę,$_
z$_
pierwiastków - na przykład dla4
tego utworzy tablicę@(4,4,4,4)
. Te elementy tablicy są następnie wpompowywane w rurę, zGet-Random
której wydobywa się jeden z elementów z (pseudo) równym prawdopodobieństwem. Ponieważ np.@(4,1,5)
Daje nam@(4,4,4,4,1,5,5,5,5,5)
to spełnienie wymagań prawdopodobieństwa.źródło
C # (.NET Core) ,
93898776 + 18 = 94 bajtówWypróbuj online!
Dodatkowe 18 bajtów dla
using System.Linq;
Podziękowanie
11 bajtów zaoszczędzonych dzięki Nevayowi, którego implementacja liczb losowych była o wiele bardziej zwięzła (a także być
int
zamiast adouble
).Degolfed
Wyjaśnienie
Uzyskaj losową liczbę
r
od 0 do sumy elementów. Następnie przy każdej iteracji odejmij bieżący elementr
. Jeślir
jest mniejsze niż0
, zwróć ten element. Chodzi o to, że są większe części liczby losowej dla większych liczb w tablicy.źródło
a=>{int i=-1,r=new Random().Next(a.Sum());for(;r>=0;)r-=a[++i];return a[i];}
Japt , 7 bajtów
Sprawdź to tutaj
Wyjaśnienie
Domniemane wejście tablicy
U
.Odwzoruj tablicę, przepuszczając każdy element przez funkcję, gdzie
D
jest bieżący element.Wygeneruj tablicę długości
D
i wypełnij jąD
.Spłaszczyć.
Zdobądź losowy element.
źródło
CJam , 5 bajtów
Wypróbuj online! Uwaga: oddziel liczby od spacji
źródło
Perl, 31 bajtów
Zakłada się, że dane wejściowe są argumentami wiersza poleceń. Pamiętaj, że może zabraknąć pamięci, jeśli liczby są duże.
źródło
Perl 5 , 31 + 1 (-a) = 32 bajty
Wypróbuj online!
źródło
GolfScript , 17 bajtów
Wypróbuj online!
źródło
Węgiel drzewny , 12 bajtów
Wypróbuj online! Link jest do pełnej wersji kodu. Ponieważ Charcoal próbuje być zbyt sprytny, muszę użyć danych rozdzielanych średnikami dla tablicy. Wyjaśnienie:
źródło
Haskell , 87 bajtów
Wypróbuj online!
źródło
JavaScript (ES6),
6154 bajtów-7 bajtów dzięki @Justin Mariner
Przykładowy fragment kodu
źródło
eval(a.join`+`)
zamiastreduce
.[].find(m=>(n-=m)<0,n=Math.random()*eval(a.join
))
input::[].find(...)
Haskell ,
7877 bajtówWypróbuj online! Przykład użycia:
f [1,99]
prawdopodobnie daje99
.Wyjaśnienie:
f
pobiera listę liczb całkowitychl
i zwraca losowo wybraną liczbę całkowitą jakoIO Int
.l>>= \n->n<$[1..n]
konstruuje listę z każdymn
powtórzonym elementemn
razy.randomRIO(0,sum l-1)
zwraca liczbę całkowitą z zakresu od 0 do długości listy powtarzanych elementów, która jest dokładnie sumą wszystkich elementów, minus jeden, aby uniknąć wyjątku spoza zakresu.Bonus: 85-bajtowa wersja bez punktów
Wypróbuj online!
źródło
Bash , 51 bajtów
Pobiera dane wejściowe rozdzielone spacją lub znakiem nowej linii w jednym argumencie lub wielu argumentach.
Wypróbuj online!
Sprawdź losowe częstotliwości w bardziej skomplikowanym przypadku testowym.
źródło
Java 8,
127122121 bajtów-1 bajt dzięki @Nevay .
Stosuje podobne podejście, jak odpowiedź Jelly @ErikTheOutgolfer , dodając
n
razy pozycjęn
do listy, a następnie wybierz jedną losowo z tej listy.Wyjaśnienie:
Wypróbuj tutaj.
źródło
#shuffle
połączenie do pętli for, aby zaoszczędzić 1 bajtfor(int j=i;j-->0;Collections.shuffle(l))l.add(i);
.Dyalog APL , 8 bajtów
Wypróbuj online!
W jaki sposób?
/⍨
,n
kopien
każdegon
w argumencie.⌷⍨
, według indeksu1?
, losowa wartość pomiędzy1
i+/
, suma argumentuźródło
GNU APL 1.2,
2623 bajtów; 1.72119 bajtówPodejście zainspirowane odpowiedzią Erika the Outgolfer's Jelly . Polega na
⎕IO
byciu 0 zamiast 1, co jest wartością domyślną dla GNU APL (rodzaj +5 bajtów dla⎕IO←0
).-3, -2 bajty dzięki @ Zacharý
∇
formularz funkcyjnyAnonimowa forma lambda
Dla wyjaśnienia użyję
⍵
do przedstawienia argumentu przekazanego do funkcji, ale jest ona równoważnaR
z∇
formą.⍵∘.⍴⍵
oblicza zewnętrzny produkt z listy za pomocą⍴
operatora reshape ( ). W efekcie tworzy to tabelę (jak tabliczka mnożenia), ale zamiast mnożenia powtarza element w kolumnie kilka razy równy elementowi w wierszu. Dla przykładu podanego w pytaniu jest to:0 0⍉⍵∘.⍴⍵
transponuje macierz i zwraca tylko główną przekątną. To daje nam tylko te części, w których wiersz i kolumna⍵∘.⍴⍵
były takie same, tzn. Powtórzyliśmy liczbę kilka razy równą jej wartości. Na przykład jest to:∊
zamienia argument w listę. Za pomocą⍉
operatora transpose ( ) otrzymaliśmy wektor zawierający 3 wektory. Enlist (∊
) zamienia go w pojedynczy wektor zawierający wszystkie elementy.S←...
przypisuje ten nowy wektor do wektoraS
.⍴S
daje nam długość tej listy.?
jest operatorem losowym, więc?⍴S
daje nam losową liczbę od 0 do długości listy (wyłączne) (dlatego opiera się na⎕IO
byciu 0; w przeciwnym razie jest między 1 a długością włącznie).S[...]
zwraca element o podanym indeksie.źródło
Q
, bo nigdy go nie używasz. I IIRC możesz usunąć znak nowej linii przed del (mała rzecz trójkątna oznaczająca koniec funkcji.)<IO> <IO>⍉
to get the main diagonal was even a thing!MATLAB, 30 bytes
This assumes MATLAB R2015a or newer and with the Statistics & Machine Learning toolbox installed.
See the explanation below for how
repelem
is used. The difference between this shorter one and the one below is that the S&ML toolbox includes the functiondatasample
which can be used to take one or more elements from an array at random (with uniform probability) which allows an anonymous function to be used, stripping away theinput/disp
calls.MATLAB, 49 bytes
This code assumes that MATLAB R2015a or newer is used as that is when the
repelem
function was introduced.repelem
is a function which takes two parameters, the first is an array of numbers to be replicated, and the second is an array of how many times the corresponding element should be replicated. Essentially the function performs run-length decoding by providing the number and the run-length.By providing the same input to both inputs of
repelem
we end up with an array which consists of n times more of element n if that makes sense. If you provided[1 2 3]
you would get[1 2 2 3 3 3]
. If you provided[1 2 4 2]
you would get[1 2 2 4 4 4 4 2 2]
. By doing this it means that if we select an element with uniform probability (randi(m)
gives a random integer from 1 to m with uniform probability), each element n has an n times higher probability of being selected. In the first example of[1 2 3]
,1
would have a 1/6 chance,2
would have a 2/6 chance and3
would have a 3/6 chance.As a side note, because
repelem
is not available yet for Octave, I can't give a TIO link. Additionally because Octave can't be used there is a big character penalty asinput()
anddisp()
need to be used as an anonymous function is not possible. If Octave supportedrepelem
, the following could be used:That would have saved 16 bytes, but it was not to be.
źródło