Twój program musi wydrukować pewną liczbę spacji, a następnie kropkę i nowy wiersz. Liczba spacji to pozycja x kropki zdefiniowana za pomocą 0 <x <30
Każda nowa linia to kolej. Twój program działa przez 30 tur. Twój program zaczyna się od losowej pozycji x i każda kolejka losowo przesuwa tę pozycję o 1 w lewo lub w prawo, pozostając w obrębie określonego obszaru. Za każdym razem twoja kropka musi zmieniać swoją pozycję o 1.
Twój wynik to liczba znaków. Otrzymasz 10 punktów bonusowych, jeśli każda drukowana linia składa się dokładnie z 30 znaków (i nowej linii). Dostajesz 50 punktów bonusowych, jeśli, choć losowo, twój program ma tendencję do pozostawania na środku określonego obszaru.
Edycja: 50 punktów bonusowych ma na celu przyciągnięcie twojej kropki do środka. Na przykład dotyczy to, jeśli twoja kropka wynosi x = 20 i ma szansę 66% na pójście w lewo i 33% na pójście w prawo. Musi to być niezależne od punktu początkowego i powinno się to odbywać jedynie poprzez dynamiczną zmianę wartości procentowej lewej / prawej.
Żadne dane wejściowe nie są dozwolone, dane wyjściowe muszą znajdować się na konsoli wykonawczej!
Dla lepszego zrozumienia, oto czytelny przykład w Javie, który dałby wynik 723:
public class DotJumper{
public static void main(String[] args){
int i = (int)(Math.random()*30);
int max = 29;
int step = 1;
int count = 30;
while(count>0){
if(i<=1){
i+=step;
}else if(i>=max){
i-=step;
}else{
if(Math.random() > 0.5){
i+=step;
}else{
i-=step;
}
}
print(i);
count--;
}
}
public static void print(int i){
while(i>0){
System.out.print(' ');
i--;
}
System.out.println('.');
}
}
int i = (int)(Math.random()*30);
powinno byćint i = 1 + (int)(Math.random()*29);
. W obecnej chwili generuje liczbę0 >= x > 30
zamiast0 > x > 30
.Odpowiedzi:
APL, 39–10–50 = –21
Testowane na Dyalog z
⎕IO←1
a⎕ML←3
, ale powinien być dość przenośne.Wyjaśnienie
Na każdym etapie kod ten decyduje, czy przesunąć kropkę w lewo czy w prawo, w zależności od prawdopodobieństwa, że liczba losowa wybrana spośród (1,5 2,5 ... 27,5 28,5) jest mniejsza niż bieżąca pozycja kropki.
Dlatego gdy bieżąca pozycja kropki (liczba spacji po lewej) wynosi 1, przyrost wynosi zawsze +1 (wszystkie te liczby 1,5 ... 28,5 są> 1), a gdy 29 to zawsze -1 (wszystkie te liczby są <29); w przeciwnym razie jest wybierany losowo między +1 a -1, z prawdopodobieństwem, które jest interpolacją liniową między tymi skrajnościami. Tak więc kropka zawsze się porusza i zawsze bardziej prawdopodobne jest przesuwanie się w kierunku środka niż w bok. Jeśli jest dokładnie pośrodku, ma 50% szans na przejście w dowolną stronę.
Zmniejszenie (prawy krotnie) powielonej wartości
{...}/a/b
to tylko sztuczka, którą wymyśliłem, aby powtórzyća-1
czasy funkcji , zaczynając od wartościb
i mając wynik każdej iteracji jako⍵
argument accumulator ( ) do następnego. Drugi i następny argument wejściowy (⍺
) oraz wynik końcowy są ignorowane. Okazuje się, że jest znacznie krótszy niż zwykłe rekurencyjne połączenie ze strażą.Przykładowy przebieg
źródło
+/2×⍳9
jest czytane „suma: dwa razy: naturals do 9”, ale jest wykonane w odwrotny sposób.⎕←30↑...
wypisze 30 znaków plus nowy wiersz, bez względu na ciąg znaków...
Mathematica 138-10-50 = 78
Nie publikuję tego, ponieważ uważam, że jest szczególnie dobrze golfowany, ale z innych powodów. Wykorzystuje definicję procesu Markowa z macierzą przejścia zaprojektowaną w celu „wyśrodkowania” piłki.
Zastosowanie procesu Markowa w Mathematica pozwala nam obliczyć przydatne statystyki , jak zobaczycie poniżej.
Najpierw kod (spacje nie są potrzebne):
Niektóre wyjścia:
Użyłem macierzy przejścia:
Ale, jak powiedziałem, interesującą częścią jest to, że użycie
DiscreteMarkovProcess[]
pozwala nam zrobić dobre zdjęcie tego, co się dzieje.Zobaczmy prawdopodobieństwo, że piłka będzie
15
w dowolnym momencie,t
zaczynając od określonego losowego stanu :Widać, że waha się między 0 a wartością bliską 0,3, to znaczy, że w zależności od stanu początkowego można osiągnąć 15 na nieparzystej lub parzystej liczbie kroków :)
Teraz możemy zrobić to samo, ale powiedzieć Mathematice, aby rozważyła statystykę, zaczynając od wszystkich możliwych stanów początkowych. Jakie jest prawdopodobieństwo bycia
15
po pewnym czasiet
?Widać, że również oscyluje ... dlaczego? Odpowiedź jest prosta: w przedziale
[1, 29]
jest więcej liczb nieparzystych niż parzystych :)Oscylacja prawie zniknęła, jeśli poprosimy o prawdopodobieństwo, że piłka znajdzie się w
14 OR 15
:Możesz też poprosić o limit (w sensie Cesaro) prawdopodobieństwa stanu:
No cóż, być może zasługuję na trochę pochlebnych odpowiedzi na taką nie-tematyczną odpowiedź. Nie krępuj się.
źródło
Bash, wynik 21 (81 bajtów - 50 premii - 10 premii)
W tej odpowiedzi kropka jest „ciągnięta” z powrotem na środek. Można to sprawdzić, wpisując punkt początkowy na 0 lub 30.
źródło
{1..30}
przez{P..m}
o
jest1
iRANDOM%30
zwraca0
? A także w następnej iteracji?Rubin
696664-60 = 4Próba:
źródło
i=rand 30;
zamiasti=rand(30);
.Smalltalk,
161159145-60 = 85wszystkie kolumny mają długość 30 znaków (operują ciągiem zmiennym b);
losowa szansa na ruch jest korygowana poprzez odchylenie wartości rnd za pomocą p (rnd (0..29) -p), przyjmując znak (-1/0/1), a następnie dostosowując do (-1 / + 1) za pomocą (-1 | 1), który jest traktowany jako delta ruchu (efektywnie oblicza: znak x <= 0 ifTrue: -1 ifFalse: 1). Ponieważ ST używa indeksowania opartego na 1, muszę skorygować wszystkie referencje ciągów o +1 (plz doceniam bicie -1 | 1-bitowy hack ;-)).
kradnąc pomysł z wersji Ruby (thanx & Up @fipgr), mogę pozbyć się kontroli min / max:
dane wyjściowe: (później ręcznie dodałem liczby kolumn i pionowe słupki; powyższy kod ich nie generuje)
źródło
C 86
Zakładając, że uruchomienie
rand()
funkcji nie jest wymagane.Wyjaśnienie:
W C,
"%*c"
o*
oznacza, że długość wyjściowy będzie miał minimalną długość, a to minimalna długość jest określana przez parametr wywołania funkcji (w tym przypadku, jest toi+=i==30?-1:i==1||rand()%2?1:-1
. Tec
środki następnego argument (46
) to znak ( kropka).Jeśli chodzi o kontrolę granic, przepraszam, że o tym zapomniałem. Dodałem to do odpowiedzi, kosztem 15 znaków. Operator trójargumentowy działa w następujący sposób:
boolean_condition?value_if_true:value_if_false
. Zauważ, że w C prawda ma wartość 1, a fałsz wynosi 0.źródło
printf("%*c\n",i+=rand()%2?1:-1,46)
drukuje spacje, a także w jaki sposób powstrzymuje kropkę przed przekroczeniem 29. Z góry dzięki. (Przepraszam, nie jestem programistą C.)rand()%2
, ponieważ jest bardzo przewidywalne (zwroty nieparzyste / parzyste)? Wypróbowałem twojerand()%2
w moim rozwiązaniu PHP i wykazało to bardzo przewidywalne zachowanie (w przeciwieństwie dorand(0,1)
. Ponieważ PHP często korzysta z bibliotek C (jeśli mam rację), zastanawiałem się, czy twój program C ma tę samą „wadę” .rand()
funkcji. W C, jeślirand()
nie jest jawnie zaszczepiony, zawsze używa tego samego ziarna za każdym razem. Dlatego jest to przewidywalne. Gdybym musiał go zaszczepić, mogę zrobić,srand(time());
co kosztuje 14 znakówrand()
nie muszą byćsrand()
już wysiewane , ale nadal wykazują to dziwne zachowanie.Java:
204183182176175 znaków - 10-50 = 115Po pierwsze, pozycja kropki musi być
0 < x < 30
, tj. [1-29]. Generuje to liczbę od 0 do 28 równomiernie rozmieszczoną, a dla celów tego programu [0-28] ma taki sam efekt jak [1-29]:Ja osobiście wolałbym, aby był normalnie rozpowszechniany około 14, ale moja odpowiedź byłaby dłuższa:
Po drugie, ten kod zapewnia, że zwykle znajduje się na środku:
Prawdopodobieństwo uzyskania +1 jest większe, ponieważ mniejsza jest wartość
i
, i mamy odwrotność dla -1. Jeślii
wynosi 0, prawdopodobieństwo uzyskania +1 wynosi 100%, a prawdopodobieństwo uzyskania -1 wynosi 0%. Jeślii
wynosi 28, to stanie się odwrotnie.Po trzecie, zamieniając
32
na końcu na,'_'
aby łatwiej zobaczyć wynik, widzimy, że każda linia ma 30 znaków plus nowy wiersz:Podziękowania dla @VadimR (obecnie użytkownik 2846289) za wskazanie nieporozumienia w poprzedniej wersji.
Dzięki @KevinCruijssen za golenie 6 znaków, nawet po ponad dwóch i pół roku od opublikowania tej odpowiedzi.
źródło
i
dojazd0
jest nielegalny, prawda?i
jest w zakresie [0–29]. Jest to równoważne z [1-30] lub [288-317], wynik byłby taki sam. Liczy się to, że w przedziale [0–29] znajduje się 30 liczb całkowitych.i
nie może być0
. Rozumiem, że chodzi przede wszystkim o dobrą zabawę, ale nadal jest to smutne.i
dostaje się na1
początku, a przy pierwszej iteracjiMath.random()
jest0
, a potemi
dostaje0
. Nie zrozum mnie źle, nie chodzi o twoją odpowiedź. Raczej o mojej niezdolności do czytania większości języków innych niż C. Zatem bez żadnej reakcji (z wyjątkiem pozytywnych opinii) na błędy, skąd mam wiedzieć, czy mają rację, czy nie?Mathematica 157-10-50 = 97
Do uruchomienia używana jest liczba losowa od 1 do 30. Wszystkie pozostałe numery kolumn z kropki są wybierane za pomocą
RandomChoice[If[c > 15, {2, 1}, {1, 2}] -> {-1, 1}] + c
, co przekłada się na: „Jeśli poprzedni numer kolumny był większy niż 15, wybierz jedną liczbę z zestawu {-1,1}, z -1 ważoną 2: 1 w odniesieniu do 1; w przeciwnym razie odwróć obciążniki i wybierz z tego samego zestawu.ReplacePart
zastępuje element na liście 30 pustych miejsc, które odpowiadają zainteresowanej kolumnie.źródło
RandomChoice[]
> <>, 358–10 = 348
W codegolf nie wygra, ale działa. (W systemie Windows 7 z systemie tym tłumaczem , który implementuje instrukcję „p” inaczej niż strona esolang ją definiuje)
Nazwy tego języka nie można wyszukiwać w Google, więc oto ciekawy artykuł w esolang .
źródło
PHP,
118113112111 (, -10 punktów bonusowych = 101)(druga próba, z okropnie przewidywalnym
rand()
zachowaniem i nieco większą wydajnością)Możliwy wynik:
PHP, 130 (, -10 punktów bonusowych = 120)
(pierwsza próba)
Prawdopodobnie mogłoby to być znacznie bardziej wydajne:
Jeśli zastąpię spację znakiem podkreślenia (do celów wyświetlania), jest to możliwy wynik:
Co dziwne, jeśli mogę wymienić
rand(0,1)
zrand()%2
(PHP 5.4 w systemie Windows XP), losowy wynik zawsze przełącza się z dziwne, nawet, i odwrotnie, na każdej kolejnej iteracji, dzięki czemurand()
niepokojąco przewidywalne, w tym sensie, wszystko nagle. Ten „błąd” wydaje się być znany od 2004 roku . Nie do końca wiadomo, czy to dokładnie ten sam „błąd”.źródło
J 42 znaki - 50-10 = -18
Wyjaśnienie, zaczynając od prawej ( przydaje się trochę wiedzy o pociągach ):
Tendencja środkowa, -50, przykład ponad 1000 przebiegów:
Przykładowy przebieg, wyświetlający dokładnie 30 bajtów w każdym wierszu
źródło
Python 2.7:
126109-10-50 = 49Pozbyłem się zakodowanego punktu początkowego - teraz zaczyna się w losowym punkcie. Z tego powodu potrzebowałem randinta, więc zdecydowałem się użyć tego zamiast wyboru dla offsetu. Zastosował do tego sztuczkę bool (-1) **.
Kilka świetnych odpowiedzi tutaj. Pierwsza próba w Pythonie, myślenie o ulepszeniach. Nie pomaga konieczność importu.
-10 - tak 30 znaków + \ n w każdej linii
-50 - im dalej od centrum, tym bardziej prawdopodobne jest przesunięcie w drugą stronę (dokonane przez zbudowanie listy z inną liczbą przesunięć + / i)
Poprzednia próba:
źródło
for
pętla może znajdować się na jednej linii, ale jeszcze lepiej jestfor i in[0]*30:
i lepiej jesteval"..."*30
.Java -
198183 znakówTo tylko prosty, prosty, bezpośredni i mało kreatywny golf z przykładu, który podałeś w pytaniu.
źródło
Partia - (288 bajtów - 10) 278
Bez golfa:
Aby wyprowadzać spacje zamiast znaków podkreślenia - 372 bajtów -
Szukając pomocy z następującą logiką, z pewnością nie jest to metoda zajmująca najwięcej miejsca (! R! Rozwinie się do 1 lub 2) -
Gra w golfa do:
if !r!==1 (if !p! GTR 1 (set/ap-=1)else set/ap+=1)else if !r! LSS 30 (set/ap+=1)else set/ap-=1
źródło
J, 42 znaki, bez bonusów
Przykładowy przebieg:
źródło
Python 2.7 (126-10 (stała długość) - 50 (Tendencja środkowa) = 66)
Poniższy program ma tendencję centralną w stosunku do większej próby
Próbny
źródło
JavaScript
125737260 (120-50 - 10)EDYCJA: Naprawiono premię 50 punktów i premię 10 punktów.
EDYCJA 2: Jeszcze krótsza!
źródło
r=Math.random;s=r()*30|0;for(i=0;i++<30;a=Array(30)){a[s=s>28?28:s?r()<s/30?s-1:s+1:1]='.';console.log(a.join(' '))}
for
działającego; musiałem zrobić chwilę.D -
167,162, 144 (154–10)Gra w golfa :
Bez golfa :
EDYCJA 1 - Nie jestem pewien, czy mój kod kwalifikuje się do premii -50, czy nie.
i
nie zawsze zaczynają się w środku, ale podczasfor
pętli, kropka przesuwa nigdy więcej niż 3 miejsc jak obu kierunkach, więc kiedyi
ma rozpocząć pobliżu środka, cała sprawa ma tendencję do pozostawania tam również.EDYCJA 2 - Kod kwalifikuje się teraz do premii -10, ponieważ drukuje tablicę 29 znaków, a następnie LF, w sumie dokładnie 30 znaków w wierszu.
źródło
PowerShell, 77–10–50 = 17
Wynik
źródło
$x=random 30;1..30|%{' '*($x+=,-1*$x+,1*(29-$x)|random)+'.'|% *ht 30}
. 66 bajtów - 10-50 = 6 punktówR, 107 znaków - bonus 60 punktów = 47
i
jest indeksem kropki.a
to tablica 30 spacji. Punkt początkowy jest losowy (jednolicie od 1 do 29). Przy każdej iteracji losowo dodajemy -1 lub +1 doi
ważonych prawdopodobieństw:i-1
dla-1
i29-i
for+1
(wartości podawane jako prawdopodobieństwa nie muszą sumować się do jednego), co oznacza, że dąży on do zorientowania kropki w kierunku środka, jednocześnie zapobiegając jej od dołu 1 lub powyżej 29 (ponieważ ich prawdopodobieństwo spada do 0 w obu przypadkach).Przykład uruchomienia z
_
zamiast spacji dla czytelności:źródło
i
możesz stać się albo,0
czy30
nie?s(1:29,1)
jes(29,1)
.C # 184–10–50 = 123
Wynik
spacezastąpione przez _dla czytelności.
źródło
if...else if...else
na końcu kodu powinien znajdować się mniejszy kod. Co więcej, twoje wyniki budzą pewne wątpliwości, że zwykle znajdują się w środku, ale twój kod wydaje się mieć rację.r.Next(30)<p?-1:1;
sprawia, że tak się dzieje. Nie jestem pewien, czy można zmniejszyć za pomocąif
instrukcji.switch
jest duży ze względu na obowiązkowebreak
/,return
a finałelse
wymagadefault:{}
sprawy i jest również długi.p
wynosi zero,p+=r.Next(30)<p?-1:1;
zawsze otrzyma 1, więc nie ma potrzebyif(p==0)
. To samo dotyczyp==29
.p
nigdy nie będzie 30, więc możesz się go pozbyćelse if
.PHP
Z premią za centrowanie: 82-50 = 32
W przypadku tej wersji (starsze wersje poniżej) usunięto sprawdzanie wartości min./maks., Jak to opisano w kodzie centrującym.
rand(1,28)
staje się tutaj ważne, ponieważ pozwala na$i++
przesuwanie się do 29 (rzeczywista maksymalna).edycja: niepotrzebny nawias, przeniesiony kod zmiany
Prosty algorytm centrowania: generuje nową liczbę od 0 do 29 i porównuje ją z bieżącą. Wykorzystuje „prawdopodobieństwo” uzyskania liczby po większej stronie, aby zbliżyć się do środka.
Rzeczywisty wynik: (później dodano numerację linii)
Zarchiwizowane:
$i=rand(0,29);for($c=0;$c++<30;){($i<1?$j=1:($i>28?$j=28:$j=rand(0,29)));($j<$i?$i--:$i++);echo pack("A$i",'').".\n";}
119 znaków$i=rand(0,29);for($c=0;$c++<30;){($i<1?$i++:($i>28?$i--:(rand(0,29)<$i?$i--:$i++)));echo pack("A$i",'').".\n";}
112 znakówźródło
JavaScript ES6 125-10 (30 linii znaków) - 50 (przesuwa się w kierunku środka) = 65
Miałem objawienie, gdy jechałem windą do mojego oddziału, więc musiałem to znieść, zanim opuściło moją pamięć ...
Trochę zmienne tasowanie pozycji i trochę kreatywności do obliczania prawdopodobieństwa przesunięcia wskazywanego przez
x/t
... (Dzięki Kostronor za wskazanie tego!) Teraz zyskuję premię -50 za przesunięcie na środek, a także osiągnąłem pozycję początkową w pełny zakres linii, co pozwoliło mi ogolić dwa bajty!źródło
15+r()*2
którym może być dowolna wartość z przedziału od 15 do 16.9999999998 lub tak, która mogłaby zaokrąglić wyłącza się na 17. dodatkowex+=r()<.5?-1:1
rzucają nieco więcej losowości, zbliżając ją do zakresu od 14 do 18, czyli technicznie losowa liczba, która mieści się w definicji tego, o co pytano ... Wyginając tę zasadę, flip (+1, -1) w większości przypadków spowoduje powrót do środka ...;)k, 53–10–50 = -7
Rozwiązanie 1
Stosowanie
Rozwiązanie 2
źródło
Scala, 95–10 = 85 bajtów
Nadal myślę o premii 50 bajtów.
Wyjaśnienie:
źródło
JavaScript, 125 (135–10)
Komentarze i porady są mile widziane.
źródło
JavaScript
114 znaków - 10 (30 linii znaków) - 50 (pociągnij kropkę w kierunku środka) = 54
Zauważyłem jednak, że nagroda za 10 znaków za wypełnienie linii do 30 znaków może być złym interesem; więc:
102 znaki - 50 (pociągnij kropkę w kierunku środka) = 52
Uznanie dla @WallyWest za uproszczony warunkowy kierunek ściągania
f()>k/29?1:-1
, mój pierwszy szkic użył dwóch zagnieżdżonych warunków.źródło
Rakieta 227 bajtów (-10 dla 30 znaków, -50 dla przejścia do linii środkowej = 167)
Na każdym kroku kropka dwa razy częściej przesuwa się w kierunku linii środkowej, niż od niej:
Nie golfowany:
Testowanie:
Wynik:
źródło