W tym pytaniu zostanie zastosowany prosty model Markowa. Aby uzyskać więcej informacji o łańcuchach Markowa, zobacz http://setosa.io/ev/markov-chains/ .
Weź sznurek. W tym przykładzie użyjemy słowa:
reader
Teraz dla każdego znaku weź znaki, które pojawiają się po każdym wystąpieniu znaku w ciągu. ( `^`
reprezentuje początek ciągu i `$`
reprezentuje koniec)
`^` -> {'r'} # After the start of the string, there is an `r`.
'r' -> {'e', `$`} # After the first `r` (*r*eader), there is an `e`
# after the second (reade*r*), there is the end of the string.
'e' -> {'a', 'r'}
'a' -> {'d'}
'd' -> {'e'}
Teraz, zaczynając od początku ciągu, wybierz losowo jedną z postaci w następnym zestawie. Dołącz tę postać, a następnie wybieraj postacie z następnego zestawu i tak dalej, aż dojdziesz do końca. Oto kilka przykładowych słów:
r
rereader
rer
readereader
Jeśli postać pojawia się wielokrotnie za inną postacią, jest bardziej prawdopodobne, że zostanie wybrana. Na przykład, cocoa can
po c
, istnieje dwie trzecie szans na uzyskanie o
i jedna trzecia szansy na uzyskanie a
.
'c' -> {'o', 'o', 'a'}
Wyzwanie
Utwórz program, który nie pobiera danych wejściowych i generuje losowy ciąg wygenerowany za pomocą łańcucha Markowa, jak powyżej, gdzie dane wejściowe do łańcucha są źródłem programu.
- Program musi mieć co najmniej dwa znaki, z których dwa muszą być takie same (aby zapobiec „nudnym” łańcuchom, które mają tylko jedno wyjście)
- Możesz zmodyfikować model, aby używać bajtów zamiast znaków, jeśli chcesz, ale zmień „znaki” na „bajty” w regule 1
- Program powinien wyprowadzać ciągi losowo z teoretyczną częstotliwością oczekiwaną
To jest golf golfowy , więc wygrywa najkrótszy program!
źródło
^
i$
w cudzysłowie? może to uczynić bardziej zrozumiałym wyciąganie go z cytatów lub umieszczanie ich w cudzysłowie.Odpowiedzi:
Pypeć , 64 bajty
To było fajne.
<tab>
reprezentuje dosłowny znak tabulacji (0x09
). Wypróbuj online!W jaki sposób?
TL; DR: składnia łańcucha znaków, repr i eval.
W przypadku ciągów, które muszą zawierać literalne
"
znaki, Pip uniknął ciągów znaków , używając ich\"
jako separatora. Standardowy quine wykorzystujący łańcuchy znaków będzie wyglądał następująco:To znaczy:
Y
ank (przechowujący jakoy
) ciąg zawierający"V Y".RPy
iV
tak dalej.RPy
pobiera repry
, do którego przygotowujemy dosłowny ciągV Y
. Na koniec wypisz wynik eval.Struktura quinu Markowa jest podobna, z tym wyjątkiem, że chcemy zapisać kod zamiast wypisywać go, a następnie zrobić z nim kilka rzeczy później.
t:V Y\"...\"
przypisuje ostateczny wynik dot
. Wewnątrz ewaluowanego kodum:"..."
przypisuje ciąg kodu, dom
którego oceniamy na końcuVm
.ST["t:V Y"RPy";Vm"C9]
buduje listę zawierającąi konwertuje go na ciąg znaków, który domyślnie łączy wszystkie elementy. Ta sekcja jest równoważna
"V Y".RPy
oryginalnej wersji Quine. Ponieważ jest to ostatnie wyrażenie w dużym ciągu eval, jego wartością jest to, coV
zwraca operator, a zatem to, do czego zostaje przypisanet
.Zatem po ewaluacji i przypisaniu
t
jest równa pełnemu kodowi im
zawieraTeraz
Vm
ocenia to jako kod. Podzielmy to, co się stanie.Kilka notatek:
xxy
zwróci tylko,xx
a niexy
w dopasowaniach. Na szczęście w tym kodzie nie ma jednak podwójnych znaków, więc nie ma to znaczenia.źródło
JavaScript,
217215 bajtówPamiętaj, że używa tego
uneval
, który jest obsługiwany tylko przez Firefox. Przykładowe przebiegi:Jak widać, jest to w większości bełkot, ale należy się tego spodziewać;) OP stworzył JSFiddle, który pokazuje, że szansa na poprawność syntaktyczną JS wynosi około 6,3%.
Gdyby dozwolone były funkcje samo-odczytu, może to być 78 bajtów ES6:
Bardzo, bardzo rzadko, powoduje to, że JS jest poprawny pod względem składniowym:
Moim ulubionym z utworzonych nazw funkcji jest
.splendom()
(split
+length
+random
)źródło
a.splerength.r()
, co może być ważne;)Perl, 103 bajty
W oparciu o standardowy quine i moją odpowiedź na to pytanie :
Przykładowy wynik
Podobnie jak inne pytanie, niektóre wyniki generują poprawny Perl:
ale szanse są nieco niższe i wynoszą ~ 2%.
źródło
q{
jest początkiem literału łańcucha i nie ma go,}
aby go zamknąć. Perl jest właściwie dość kiepski w uruchamianiu losowych sekwencji bajtów (a kiedy to robi, zwykle dzieje się tak z powodu wczesnego literału lub komentarza).Kod maszynowy MS-DOS (plik .COM), 63 bajty - niekonkurujący
Nie konkuruje, ponieważ quine nie może uzyskać dostępu do własnego kodu źródłowego.
Wariant 126-bajtowy spełniałby wymóg „nie uzyskiwania dostępu do własnego kodu źródłowego”!
63-bajtowy wariant wygląda następująco:
Nie jestem również pewien rozkładu prawdopodobieństwa generatora losowego:
Program wykorzystuje fakt, że liczniki zegara i inne informacje zmodyfikowane przez przerwania są przechowywane w segmencie 0 w celu wygenerowania liczb losowych.
Przykłady generowanych wyników to:
Program przekonwertowany na kod asemblera wygląda następująco:
źródło
C 306
328585611615623673707bajtyKod źródłowy:
Z dodanymi znakami i białymi znakami dla czytelności / objaśnienia:
Wyjaśnienie
Line 01
:p[][]
przechowuje liczby kolejnych znaków.Line 02
:X
zawiera źródło programu, wraz z klawiszem Esc%c%s%c
.Line 03
:Y
będzie zawierał dosłowne źródło programu.c
,j
,*a
Są zmiennymi liczenia.Line 05
: ZestawY
zawiera quine.Line 06
: Policz wystąpienia liter wp[][]
.Line 07
: Wydrukuj bieżący stan.Line 08
: Znajdź następną postać losowo, proporcjonalnie do liczbyp[][]
.Przykładowe dane wyjściowe:
p[++);p[99]=Y;putfor(aind(a++j,*a+j=j,c][c,*an(arile(pr*Y,Y[256]<<1);)][*Y,Y;)wha+++j=*aintfor*Y;prin(a+j]=j][256<1)pr(a;a;f(p[char(Y;for());};a;ma;ma=%s%chain(Y;ar(j][256<<<1)p[256<<raile(cha][9]<rin(j,34,34,Y[256]+j,Y,34,Y,c=Y,*a;*a;for(){0}
źródło
Rubin, 152 bajty
Przykładowe dane wyjściowe:
lub
Quines używa formatowania łańcuchów przez
"s%s"
i wykonuje łańcuch Markowa, biorąc wszystkie dwuznakowe plastry, tasując je i przekształcając w słownik Hash, w którym dla duplikatów kluczy ostatni wygląd określa wartość. Aby uniknąć dodawania dodatkowej logiki na początku, śledzę ostatnio używany znak wyjściowy$/
, który jest automatycznie inicjowany do nowej linii, i upewniam się, że po linii nowej zawsze następuje po0
tym samym znaku, od którego zaczyna się kod. Na koniec manipuluję kodem źródłowym, aby był tylko jeden,!
więc zawsze kończymy po huku,<<33
dodając go bez literału. Można to jeszcze pograć w golfa za pomocą jednocyfrowego znaku niedrukowalnego zamiast ASCII 33, ale wydawało się to zbyt denerwujące.źródło
p<<<<<33
Operator super-super-super-konkat? ;-)Has(s).ears(2)
wywołuje u mnie chichot!Rdza, 564 bajty (niekonkurencyjne)
Ponieważ napisałem już całkiem porządny cytat z Rust na inne pytanie, pomyślałem, że dostosuję go do tego, ponieważ wydawało się to dość proste. Chociaż oryginał był niewielki, w tym celu bardzo mało próbowałem zminimalizować rozmiar. Oto rozszerzona wersja wyjaśniająca, co się dzieje:
Przykładowy wynik 1:
Przykładowe wyjście 2:
źródło
Python 2, 211 bajtów
Wysyła wynik do
stderr
.Wypróbuj online
Przykładowe dane wyjściowe:
Krótkie wyjaśnienie:
s='s=%r;print s%%s';print s%s
formatu quine. Tworzę ciągs
, który będzie zawierał cały program.X
zawiera procedurę rekurencyjną.o
, do którego zostanie wydrukowanystderr
po osiągnięciu końca łańcucha Markowa.$$
, używając dwóch znaków, dzięki czemu program będzie działał dla wszystkich ciągów. Mógłbym użyć postaci, której nie ma w moim programiechr(0)
, ale myślę, że to dłużej.c
, który (wraz zo
) jest inicjowany do pierwszego znaku programu.c
w ciągut
(zmienna zawierająca quine kodu źródłowego) toq
, z której wybierany będzie następny wybórc
.źródło
PHP,
144135130120272220212 bajtówLub sformatowane pod kątem czytelności:
Przykładowe dane wyjściowe:
i:
i:
i:
Oszukiwanie PHP, 117
Dla ciekawskich, jeśli oszukujemy czytając własne źródło, możemy zrobić 117:
źródło