Zagraj w golfa na dobre!


204

Używając wybranego języka, zagraj w golfa .

Quine to program niepusty komputerowy, który nie bierze wejście i tworzy kopię własnego kodu źródłowego jako jedynego wyjścia.

Bez oszustwa - oznacza to, że nie można po prostu odczytać pliku źródłowego i wydrukować go. Również w wielu językach pusty plik jest również quine: to również nie jest uważane za quine.

Brak quinesów błędów - istnieje już osobne wyzwanie dla quinesów błędów.

Punkty za:

  • Najmniejszy kod (w bajtach)
  • Najbardziej zaciemnione / niejasne rozwiązanie
  • Używanie ezoterycznych / niejasnych języków
  • Z powodzeniem używa języków, w których trudno grać w golfa

Poniższego fragmentu stosu można użyć, aby uzyskać szybki podgląd bieżącego wyniku w każdym języku, a tym samym wiedzieć, które języki mają istniejące odpowiedzi i jaki cel należy pokonać:


4
Nie masz na myśli: „Golf ci quine dla większego dobra!”?
Mateen Ulhaq

50
@muntoo to gra na „Learn you a Haskell for Great Good”.
Rafe Kettler

Odpowiedzi:


106

Sześciokąty , długość boku 17 16, 816 705 bajtów

180963109168843880558244491673953327577233938129339173058720504081484022549811402058271303887670710274969455065557883702369807148960608553223879503892017157337685576056512546932243594316638247597075423507937943819812664454190530214807032600083287129465751195839469777849740055584043374711363571711078781297231590606019313065042667406784753422844".".>.@.#.#.#.#.#.#.#.>.(...........................<.".......".".>./.4.Q.;.+.<.#.>...........................<.".....".".>.#.#.>.N.2.'.\.>.............=.=......._.<.".....".".>.>.;.'.=.:.\.>.......................<."...".".>.\.'.%.'.<.#.>..............._.....<."...".".>.#.#.>.<.#.>...............=.=.<.".".".>.#.\.'.R./.>.................<.".!.........../.>.

Wypróbuj online!

Oto jak wygląda rozwinięta:

                1 8 0 9 6 3 1 0 9 1 6 8 8 4 3 8
               8 0 5 5 8 2 4 4 4 9 1 6 7 3 9 5 3
              3 2 7 5 7 7 2 3 3 9 3 8 1 2 9 3 3 9
             1 7 3 0 5 8 7 2 0 5 0 4 0 8 1 4 8 4 0
            2 2 5 4 9 8 1 1 4 0 2 0 5 8 2 7 1 3 0 3
           8 8 7 6 7 0 7 1 0 2 7 4 9 6 9 4 5 5 0 6 5
          5 5 7 8 8 3 7 0 2 3 6 9 8 0 7 1 4 8 9 6 0 6
         0 8 5 5 3 2 2 3 8 7 9 5 0 3 8 9 2 0 1 7 1 5 7
        3 3 7 6 8 5 5 7 6 0 5 6 5 1 2 5 4 6 9 3 2 2 4 3
       5 9 4 3 1 6 6 3 8 2 4 7 5 9 7 0 7 5 4 2 3 5 0 7 9
      3 7 9 4 3 8 1 9 8 1 2 6 6 4 4 5 4 1 9 0 5 3 0 2 1 4
     8 0 7 0 3 2 6 0 0 0 8 3 2 8 7 1 2 9 4 6 5 7 5 1 1 9 5
    8 3 9 4 6 9 7 7 7 8 4 9 7 4 0 0 5 5 5 8 4 0 4 3 3 7 4 7
   1 1 3 6 3 5 7 1 7 1 1 0 7 8 7 8 1 2 9 7 2 3 1 5 9 0 6 0 6
  0 1 9 3 1 3 0 6 5 0 4 2 6 6 7 4 0 6 7 8 4 7 5 3 4 2 2 8 4 4
 " . " . > . @ . # . # . # . # . # . # . # . > . ( . . . . . .
  . . . . . . . . . . . . . . . . . . . . . < . " . . . . . .
   . " . " . > . / . 4 . Q . ; . + . < . # . > . . . . . . .
    . . . . . . . . . . . . . . . . . . . . < . " . . . . .
     " . " . > . # . # . > . N . 2 . ' . \ . > . . . . . .
      . . . . . . . = . = . . . . . . . _ . < . " . . . .
       . " . " . > . > . ; . ' . = . : . \ . > . . . . .
        . . . . . . . . . . . . . . . . . . < . " . . .
         " . " . > . \ . ' . % . ' . < . # . > . . . .
          . . . . . . . . . . . _ . . . . . < . " . .
           . " . " . > . # . # . > . < . # . > . . .
            . . . . . . . . . . . . = . = . < . " .
             " . " . > . # . \ . ' . R . / . > . .
              . . . . . . . . . . . . . . . < . "
               . ! . . . . . . . . . . . / . > .
                . . . . . . . . . . . . . . . .

Ah dobrze, to było dość emocjonalny rollercoaster ... Przestałem liczyć ile razy przeszedłem między „haha, to szaleństwo” i „czekaj, czy ja to powinna ona być w rzeczywistości dość wykonalne”. Ograniczenia nałożone na kod przez reguły układu Hexagony były ... poważne.

Możliwe jest zmniejszenie długości boku o 1 lub 2 bez zmiany ogólnego podejścia, ale będzie to trudne (tylko komórki z #są obecnie nieużywane i dostępne dla dekodera). W tej chwili nie mam też absolutnie żadnych pomysłów na bardziej efektywne podejście, ale jestem pewien, że takie istnieje. Zastanowię się nad tym przez kilka następnych dni i może spróbuję zagrać w golfa z boku, zanim dodam wyjaśnienie i wszystko.

Przynajmniej udowodniłem, że to możliwe ...

Niektóre skrypty CJam dla własnego odniesienia:


51
Drogi Piotrze, co to jest.
Conor O'Brien

2
Jak długo to trwało?
Adnan

3
@AandN Od wczoraj bawię się pomysłami na ogólny „szablon” (co nie wymagało żadnych faktycznych testów ... po prostu wpisując jakieś rzeczy na siatce 7x7 i sprawdzając, czy to może zadziałać .. Odrzuciłem prawdopodobnie już kilka podejść już tam). Właściwe kodowanie zajęło dziś wieczorem ... może 3 godziny.
Martin Ender

10
Słowa nie potrafią wyjaśnić, jak jestem zdumiony, widząc to krok po kroku za pomocą Esoteric IDE ... Komu może się to przydać, ten sześciokąt koduje część „dekodującą” w liczbę całkowitą, która jest drukowana za pomocą, !a następnie za pomocą lustro /w 2. ostatnim wierszu wchodzi do dekodera, aby wydrukować kod dekodera, aby zakończyć quine. Ma to cudowne zastosowanie <i >odczytuje wielowierszową bardzo dużą liczbę całkowitą i buduje obszar do przechowywania dekodera. Naprawdę chciałbym wiedzieć, jakie „dziesiątki podejść” są brane pod uwagę?
Sunny Pun

3
Wyjaśnienie? ---
MD XF

77

MySQL, 167 znaków

SELECT REPLACE(@v:='SELECT REPLACE(@v:=\'2\',1+1,REPLACE(REPLACE(@v,\'\\\\\',\'\\\\\\\\\'),\'\\\'\',\'\\\\\\\'\'));',1+1,REPLACE(REPLACE(@v,'\\','\\\\'),'\'','\\\''));

Zgadza się. :-)

Naprawdę sam to napisałem. Został pierwotnie opublikowany na mojej stronie .


72

GolfScript, 2 bajty

1

(uwaga kończąca nowy wiersz) Spycha liczbę 1 na stos. Na końcu programu GolfScript drukuje wszystkie elementy na stosie (bez spacji między nimi), a następnie drukuje nowy wiersz.

To jest prawdziwa quine (jak podano w pytaniu), ponieważ faktycznie wykonuje kod; nie tylko „odczytuje plik źródłowy i drukuje go” (w przeciwieństwie do przesyłania PHP).


Dla innego przykładu, oto program GolfScript do wydrukowania 12345678:

9,(;
  1. 9: pchnij 9 na stos
  2. ,: zużyj 9 jako argument, pchnij tablicę [0 1 2 3 4 5 6 7 8]na stos
  3. (: używaj tablicy jako argumentu, wsuń tablicę [1 2 3 4 5 6 7 8]i element 0na stos
  4. ;: odrzuć najwyższy przedmiot ze stosu

Stos zawiera teraz tablicę [1 2 3 4 5 6 7 8]. Zostanie to zapisane na standardowe wyjście, bez spacji między elementami, a następnie nowy wiersz.


18
Lub PowerShell lub PHP :-)
Joey

6
Nie cofnąłeś się w czasie i nie dałeś wynalazcy pomysłu na wynalezienie GolfScript, prawda?
Mateen Ulhaq

78
Technicznie rzecz biorąc, 1nie jest quine w GolfScript: wypisuje 1\n, gdzie \noznacza nową linię. Jednak program dwóch znaków 1\n jest quine.
Ilmari Karonen,

17
Program jednoznakowy \nprawdopodobnie też jest?
Lynn

10
@Pseudonim quine to dosłownie program, który drukuje własne źródło. Nie sądzę, żeby były jakieś arbitralne ograniczenia dotyczące „struktury”.
Hugo Zink,

71

Brain-Flak , 9,8e580 1,3e562 9,3e516 12818 11024 4452 4332 4240 4200 4180 3852 3656 3616 3540 2485 + 3 = 2488 bajtów

Teraz mieści się w obserwowalnym wszechświecie!

(())(()()())(())(())(()()())(())(())(()()())(())(()()()()())(()())(()()()()())(())(()()())(())(()()()()())(())(())(())(())(()()()()())(())(())(()()())(())(())(()()())(())(()()()()())(()())(()()()()())(())(()()())(())(()()()()())(())(())(())(())(())(())(()())(())(())(())(()())(()()()())(())(()()()()())(()())(()())(()())(()()())(())(()())(())(()()()()())(()())(()()()()())(())(())(())(())(())(()())(())(())(())(()()()()())(())(())(()()()()())(())(())(()()()()())(())(())(()())(())(()())(())(()())(())(()())(())(()())(()())(()())(()())(()())(()())(()())(()())(())(()()()()())(())(())(()()())(())(())(()()())(())(()()()()())(()())(()()()()())(())(()()())(())(())(()()())(()())(())(()()()()())(())(())(()()())(())(())(()()())(())(()()()()())(()())(()()()()())(())(())(())(()()())(())(())(()()())(())(())(()()())(())(()()()()())(()())(()()()()())(()()())(())(()()())(())(())(())(()())(()()())(()())(())(()()()()())(()())(())(()()())(())(()()()()())(())(())(())(()()())(())(())(())(()())(())(()())(()()()())(())(())(()()()()())(()())(()())(())(()()())(())(())(())(())(()()())(()())(())(())(()()()()())(())(())(()()()()())(())(())(()()()()())(())(())(()())(())(()())(())(()())(())(()())(()())(()())(()())(())(()()()()())(()())(())(()()())(())(()()()()())(()()()()())(())(()()())(())(())(()())(())(()()()()())(())(()()()()())(())(())(())(()()()()())(())(())(()())(())(()())(())(()())(())(()())(())(()())(()())(()())(()())(())(()()()()())(()())(())(()()())(())(())(()())(())(()()()()())(()())(()()()()())(())(()()())(())(())(()()()()())(())(()()()()())(())(())(())(()())(())(()()()()())(())(())(()())(())(()())(())(()())(()())(()())(()())(())(()()()()())(()())(())(()()()()())(())(()()())(())(())(()())(())(()()()()())(()())(()()()()())(())(()()())(())(())(())(()())(()()()())(())(())(()())(())(()()()()())(())(())(()()()()())(())(())(()()()()())(())(())(()())(())(()())(())(()())(())(()())(())(()())(()())(()())(()())(()())(()())(())(()()())(())(())(()())(())(()()()()())(()())(()()()()())(()()())(())(())(()())(())(())(()()()()())(()()()())(()())(()())(()()())(())(()())(())(()()()()())(()())(()()()()())(())(())(())(()()()())(()()()())(()())([[]]){({}()<(([{}]())<{({}())<>(((((()()()()()){}){}){}())[()])<>{({}())<>{}({}(((()()()){}())){}{})<>{({}())<>({}(((()()()()()){})){}{}())<>{{}<>({}(((()()()()){}){}){})(<>)}}<>(({})[()()])<>}}{}<>({}(<()>)<><{({}<>)<>}<>>){({}<>)<>}{}(<>)<>{({}<>)<>}{}(((((((()()()()()){}){}){}))()))>){({}()<((({}[()])()))>)}{}<>{({}<>)<>}{}>)}{}<>{({}<>)<>}<>

Wypróbuj online!


Wyjaśnienie

Quine działa jak większość Quines w językach ezoterycznych; ma dwie części: enkoder i dekoder. Koder zawiera wszystkie nawiasy na początku, a dekoder jest bardziej złożoną częścią na samym końcu.

Naiwnym sposobem kodowania programu byłoby umieszczenie wartości ASCII każdego znaku w dekoderze na stosie. To nie jest zbyt dobry pomysł, ponieważ Brain-Flak używa tylko 8 znaków ( ()<>[]{}), więc w końcu płacisz sporo bajtów, aby zakodować bardzo mało informacji. Mądrzejszym i dotychczas stosowanym jest przypisanie każdego z 8 nawiasów klamrowych do znacznie mniejszej liczby (1-8) i przekonwertowanie ich na wartości ASCII za pomocą naszego dekodera. Jest to miłe, ponieważ kodowanie znaku kosztuje nie więcej niż 18 bajtów, w przeciwieństwie do wcześniejszych 252.

Jednak ten program nie działa. Opiera się na fakcie, że wszystkie programy Brain-Flak są zbalansowane do kodowania 8 nawiasów klamrowych z liczbami do 5. Koduje je w następujący sposób.

(       -> 2
<       -> 3
[       -> 4
{       -> 5
),>,],} -> 1

Wszystkie zamknięte nawiasy klamrowe mają przypisaną wartość 1, ponieważ możemy użyć kontekstu, aby określić, którego z nich musimy użyć w danym scenariuszu. Może to zabrzmieć jak zniechęcające zadanie dla programu Brain-Flak, ale tak naprawdę nie jest. Weźmy na przykład następujące kodowanie z odkodowanymi otwartymi nawiasami klamrowymi i zamienionymi nawiasami klamrowymi na .:

(.
((..
<([.{...

Mam nadzieję, że widać, że algorytm jest dość prosty, czytamy od lewej do prawej, za każdym razem, gdy napotykamy otwarty nawias klamrowy, przesuwamy jego wąski nawias klamrowy do wyimaginowanego stosu, a gdy napotkamy wartość .nawijamy najwyższą wartość i umieszczamy ją w miejscu .. To nowe kodowanie oszczędza nam ogromną liczbę bajtów w koderze, tracąc jedynie garść bajtów w dekoderze.

Objaśnienie niskiego poziomu

Praca w toku


25
Myślę, że wygrywasz za najdłuższe rozwiązanie wyzwania golfowego ...
Mego

18
Właśnie stał się największym pojedynczym golfem w historii PPCG Nope. 9,8e580 wciąż robi jednak wrażenie.
Dennis

19
+1 za dopasowanie do obserwowalnego wszechświata. Ponadto w przypadku TIO Nexus bezpośredni link powinien pasować do odpowiedzi. tio.run/nexus/…
Dennis,

3
... bardzo duży golf ...
Destructible Lemon

3
Myślę, że wygrywasz w przypadku większości bajtów odciętych
Christopher

68

Preludium , 5157 4514 2348 1761 1537 664 569 535 423 241 214 184 178 175 169 148 142 136 133 bajtów

Dzięki Sp3000 za oszczędność 3 bajtów.

To jest dość długie ... (dobra, wciąż jest długie ... przynajmniej pokonuje najkrótszą znaną Brainfuck C # quine w tym wyzwaniu), ale jest to pierwsza quine, którą sam odkryłem (moje zgłoszenia Lua i Julii są tak naprawdę tłumaczeniami standardowych technik quine na inne języki) i, o ile mi wiadomo, do tej pory nikt nie napisał quine w Preludium, więc jestem z tego naprawdę dumny. :)

7( -^^^2+8+2-!( 6+ !
  ((#^#(1- )#)8(1-)8)#)4337435843475142584337433447514237963742423434123534455634423547524558455296969647344257)

Ta duża liczba cyfr to tylko kodowanie kodu podstawowego, dlatego quine jest tak długi.

Cyfry kodujące quine zostały wygenerowane za pomocą tego skryptu CJam .

Wymaga to zgodnego ze standardami interpretera, który drukuje znaki (używając wartości jako kodów znaków). Więc jeśli używasz interpretera Python , musisz ustawić NUMERIC_OUTPUT = False.

Wyjaśnienie

Po pierwsze, kilka słów o Preludium: każda linia w Preludium jest osobnym „głosem”, który manipuluje własnym stosem. Te stosy są inicjowane do nieskończonej liczby zer. Program jest wykonywany kolumna po kolumnie, gdzie wszystkie polecenia w kolumnie są wykonywane „jednocześnie” na podstawie poprzednich stanów stosu. Cyfry są wypychane na stos indywidualnie, więc 42popchną a 4, a następnie a 2. Nie ma możliwości bezpośredniego wypychania większych liczb, musisz je dodać. Wartości można skopiować z sąsiednich stosów za pomocą vi ^. Pętle w stylu Brainfuck można wprowadzić w nawiasach. Zobacz link w nagłówku, aby uzyskać więcej informacji.

Oto podstawowa idea quine: najpierw pchamy ładunki cyfr na stos kodujący rdzeń quine. Wspomniany rdzeń następnie pobiera te cyfry, dekoduje je w celu wydrukowania, a następnie drukuje cyfry w postaci, w jakiej pojawiają się w kodzie (i na końcu )).

Jest to nieco skomplikowane przez fakt, że musiałem podzielić rdzeń na wiele linii. Początkowo miałem kodowanie na początku, ale potem musiałem uzupełnić pozostałe wiersze taką samą liczbą spacji. Właśnie dlatego początkowe wyniki były tak duże. Teraz umieściłem kodowanie na końcu, ale oznacza to, że najpierw muszę pominąć rdzeń, a następnie przesunąć cyfry i wskoczyć z powrotem na początek i wykonać drukowanie.

Kodowanie

Ponieważ kod ma tylko dwa głosy, a przyleganie jest cykliczne ^i vjest synonimem. To dobrze, ponieważ vma jak dotąd największy kod znakowy, więc unikanie go zawsze przy użyciu ^ułatwia kodowanie. Teraz wszystkie kody znaków mieszczą się w zakresie od 10 do 94 włącznie. Oznacza to, że mogę zakodować każdy znak dokładnie dwoma cyframi dziesiętnymi. Jest jednak jeden problem: niektóre znaki, zwłaszcza linia, mają zero w reprezentacji dziesiętnej. Jest to problem, ponieważ zer nie można łatwo odróżnić od dolnej części stosu. Na szczęście istnieje proste rozwiązanie tego problemu: wyrównujemy kody znaków 2, więc mamy zakres od 12 do 96 włącznie, który nadal wygodnie mieści się w dwóch cyfrach dziesiętnych. Teraz ze wszystkich znaków, które mogą pojawić się w programie Preludium,0ma 0 w swojej reprezentacji (50), ale tak naprawdę wcale nie potrzebujemy 0. Więc takiego kodowania używam, wypychając każdą cyfrę z osobna.

Ponieważ jednak pracujemy ze stosem, reprezentacje są wypychane w odwrotnej kolejności. Więc jeśli spojrzysz na koniec kodowania:

...9647344257

Podziel na pary i odwróć, następnie odejmij dwa, a następnie wyszukaj kody znaków:

57 42 34 47 96
55 40 32 45 94
 7  (     -  ^

gdzie 32odpowiada spacjom. Rdzeń wykonuje dokładnie tę transformację, a następnie drukuje znaki.

Rdzeń

Spójrzmy więc, jak te liczby są faktycznie przetwarzane. Po pierwsze, należy zauważyć, że pasujące nawiasy nie muszą znajdować się w tej samej linii w Preludium. Może istnieć tylko jeden nawias na kolumnę, więc nie ma dwuznaczności, w której nawiasy należą do siebie. W szczególności pionowe położenie nawiasu zamykającego jest zawsze nieistotne - stos, który jest sprawdzany w celu ustalenia, czy pętla się kończy (lub jest całkowicie pomijany), zawsze będzie tym, który ma (.

Chcemy uruchomić kod dokładnie dwa razy - za pierwszym razem pomijamy rdzeń i wypychamy wszystkie liczby na końcu, za drugim razem uruchamiamy rdzeń. W rzeczywistości, po uruchomieniu rdzenia, ponownie wypchniemy wszystkie te liczby, ale ponieważ pętla kończy się później, nie ma to znaczenia. To daje następujący szkielet:

7(
  (                   )43... encoding ...57)

Najpierw wciskamy a 7na pierwszy głos - jeśli tego nie zrobimy, nigdy nie wejdziemy w pętlę (dla szkieletu ważne jest tylko, że nie jest to zero ... dlaczego konkretnie 7zobaczymy później) . Następnie wchodzimy do głównej pętli. Teraz drugi głos zawiera kolejną pętlę. Przy pierwszym przejściu pętla zostanie pominięta, ponieważ drugi stos jest pusty / zawiera tylko 0. Skaczemy więc prosto do kodowania i wypychamy wszystkie te cyfry na stos. 7Nam nasunąć pierwszego stosu nadal istnieje, więc powtarza pętlę.

Tym razem jest też 7na drugim stosie, więc wchodzimy w pętlę na drugim głosie. Pętla drugiego głosu jest tak zaprojektowana, że ​​stos jest znowu pusty na końcu, więc działa tylko raz. Będzie ona również wyczerpywać pierwszego stosu ... Więc kiedy wyjeżdżamy pętlę na drugim głosem, ponownie wcisnąć wszystkie cyfry, ale teraz 7na pierwszym stosie została odrzucona, więc główne końce pętli i program kończy.

Następnie spójrzmy na pierwszą pętlę w rzeczywistym rdzeniu. Robienie rzeczy jednocześnie z (lub )jest dość interesujące. Tutaj zaznaczyłem korpus pętli =:

-^^^2+8+2-!
(#^#(1- )#)
 ==========

Oznacza to, że kolumna zawierająca (nie jest uważana za część pętli (znaki tam wykonywane są tylko raz, nawet jeśli pętla zostanie pominięta). Ale kolumna zawierająca ) jest częścią pętli i jest uruchamiana raz na każdej iteracji.

Zaczynamy od jednego -, który zmienia 7pierwszy stos w -7... znowu, więcej o tym później. Co do faktycznej pętli ...

Pętla trwa, dopóki stos cyfr nie został opróżniony. Przetwarza dwie cyfry jednocześnie. Celem tej pętli jest dekodowanie kodowania, wydrukowanie znaku i jednoczesne przesunięcie stosu cyfr na pierwszy głos. Więc ta część pierwsza:

^^^
#^#

Pierwsza kolumna przenosi cyfrę o 1 głos na pierwszy głos. Druga kolumna kopiuje 10 cyfr na pierwszy głos, jednocześnie kopiując 1 cyfrę z powrotem na drugi głos. Trzecia kolumna przenosi tę kopię z powrotem do pierwszego głosu. Oznacza to, że pierwszy głos ma teraz 1 cyfrę dwa razy, a 10 cyfr pomiędzy. Drugi głos ma tylko kolejną kopię 10-cyfrowej. Oznacza to, że możemy pracować z wartościami na wierzchach stosów i mieć pewność, że na pierwszym stosie pozostaną dwie kopie na później.

Teraz odzyskujemy kod znaków z dwóch cyfr:

2+8+2-!
(1- )#

Dno to mała pętla, która zmniejsza dziesięciocyfrową liczbę do zera. Do każdej iteracji chcemy dodać 10 na górę. Pamiętaj, że pierwszy 2nie jest częścią pętli, więc ciało pętli faktycznie +8+2dodaje 10 (używając 2wcześniej wypychanego), a wypycha kolejne 2. Więc kiedy skończymy z pętlą, pierwszy stos faktycznie ma podstawę 10 wartości i kolejne 2. Odejmujemy 2 z, -aby uwzględnić przesunięcie w kodowaniu i drukujemy znak za pomocą !. Po #prostu odrzuca zero na końcu dolnej pętli.

Po zakończeniu tej pętli drugi stos jest pusty, a pierwszy stos przechowuje wszystkie cyfry w odwrotnej kolejności (i a -7na dole). Reszta jest dość prosta:

( 6+ !
8(1-)8)#

Jest to druga pętla rdzenia, która teraz drukuje wszystkie cyfry. Aby to zrobić, musimy wpisać 48 do każdej cyfry, aby uzyskać poprawny kod znaku. Robimy to za pomocą prostej pętli, która uruchamia 8czasy i dodaje za 6każdym razem. Wynik jest drukowany za pomocą, !a 8na końcu jest do następnej iteracji.

A co z -7? Tak, 48 - 7 = 41który jest kodem postaci ). Magia!

Wreszcie, kiedy skończymy z tą pętlą, odrzucamy tę, 8którą właśnie nacisnęliśmy #, aby upewnić się, że zostawiamy zewnętrzną pętlę na drugim głosie. Naciskamy ponownie wszystkie cyfry, a program się kończy.



19
Martin, musisz gdzieś się zatrzymać.
patrz

3
Uwielbiam to, że ma w sumie ponad 5000 bajtów, plus potwierdzenie dla Sp3000 za uratowanie 3 z nich.
Kamil Drakari

2
@KamilDrakari To były ostatnie 3 bajty, więc to całkiem spora sprawa. ;)
Martin Ender

57

Sześciokąt , długość boku 11, 314 bajtów

164248894991581511673077637999211259627125600306858995725520485910920851569759793601722945695269172442124287874075294735023125483.....!/:;.........)%'=a':\....................\...................\..................\.................\................\...............\..............\..$@.........\$><>'?2='%.<\:;_;4Q

Wypróbuj online!


Starsza wersja:

Sześciokąt , długość boku 11, 330 bajtów

362003511553420961423766261426252539048636523959468260999944549820033581478284471415809677091006384959302453627348235790194699306179..../:{;+'=1P'%'a{:..\.....................\...................\..................\.................\................\...............\..............\.............\!$><........\..@>{?2'%<......:;;4Q/

Wypróbuj online!

Enkoder: Wypróbuj online!

Program jest mniej więcej równoważny z tym kodem Python: Wypróbuj online!

Rozłożony kod:

           3 6 2 0 0 3 5 1 1 5 5
          3 4 2 0 9 6 1 4 2 3 7 6
         6 2 6 1 4 2 6 2 5 2 5 3 9
        0 4 8 6 3 6 5 2 3 9 5 9 4 6
       8 2 6 0 9 9 9 9 4 4 5 4 9 8 2
      0 0 3 3 5 8 1 4 7 8 2 8 4 4 7 1
     4 1 5 8 0 9 6 7 7 0 9 1 0 0 6 3 8
    4 9 5 9 3 0 2 4 5 3 6 2 7 3 4 8 2 3
   5 7 9 0 1 9 4 6 9 9 3 0 6 1 7 9 . . .
  . / : { ; + ' = 1 P ' % ' a { : . . \ .
 . . . . . . . . . . . . . . . . . . . . \
  . . . . . . . . . . . . . . . . . . . \ 
   . . . . . . . . . . . . . . . . . . \  
    . . . . . . . . . . . . . . . . . \   
     . . . . . . . . . . . . . . . . \    
      . . . . . . . . . . . . . . . \     
       . . . . . . . . . . . . . . \      
        . . . . . . . . . . . . . \       
         ! $ > < . . . . . . . . \        
          . . @ > { ? 2 ' % < . .         
           . . . . : ; ; 4 Q / .          

Dwa . s zajmuje 1 bit. Wszelkie inne znaki wymagają 1 bitu i cyfry podstawowej 97.

Wyjaśnienie

Kliknij na zdjęcia, aby powiększyć. Każda część objaśnienia ma odpowiedni kod Pythona, który pomaga zrozumieć.

Część danych

Zamiast skomplikowanej strukturze stosowanych w niektórych innych odpowiedzi (z <, "i kilka innych rzeczy), po prostu niech IP przechodzą przez dolną połowę.

Data

Po pierwsze, adres IP przebiega przez wiele liczb, no-op's ( .) i mirrors ( \). Każda cyfra dołącza się do liczby w pamięci, więc na koniec wartość pamięci jest równa liczbie na początku programu.

mem = 362003511...99306179

! drukuje to,

stdout.write(str(mem))

i $skacze przez następne> .

Począwszy od <. Jeśli wartość pamięci memjest fałszywa ( <= 0tzn. Warunek mem > 0nie jest spełniony), zakończyliśmy drukowanie programu i powinniśmy wyjść. Adres IP podążałby górną ścieżką.

Exit

(pozwól, aby adres IP działał na całym świecie dla około 33 poleceń przed naciśnięciem przycisku @(co kończy program), ponieważ umieszczenie go w dowolnym miejscu powoduje dodatkowe bajty)

Jeśli to prawda, podążamy niższą ścieżką, zostajemy przekierowani kilka razy i wykonujemy jeszcze kilka poleceń, zanim trafimy na inny warunek.

# Python                    # Hexagony
# go to memory cell (a)     # {
a = 2                       # ?2
# go to memory cell (b)     # '
b = mem % a                 # %

Teraz pamięć wygląda następująco:

Mem1

Jeśli wartość jest prawdziwa:

if b > 0:

wykonywany jest następujący kod:

# Python                    # Hexagony
b = ord('Q')                # Q
b = b*10+4                  # 4
# Note: now b == ord('.')+256*3
stdout.write(chr(b%256))    # ;
stdout.write(chr(b%256))    # ;

Zobacz szczegółowe wyjaśnienie Q4co MartinEnder za HelloWorld Hexagony odpowiedź . Krótko mówiąc, ten kod jest drukowany .dwukrotnie.

Pierwotnie planowałem, aby to .raz wydrukować . Kiedy wymyśliłem to (wydrukowałem .dwa razy) i wdrożyłem, zapisano około 10 cyfr.

Następnie,

b = mem // a                # :

Oto ważny fakt, z którego zdałem sobie sprawę, że zapisałem mi około 14 cyfr: Nie musisz być w miejscu, w którym zacząłeś.


Aby zrozumieć, co mówię, posłuchajmy analogii BF. (pomiń to, jeśli już zrozumiałeś)

Biorąc pod uwagę kod

while a != 0:
    b, a = a * 2, 0
    a, b = b, 0
    print(a)

Zakładając, że możemy abyć wartością bieżącej komórki i bbyć wartością prawej komórki, proste tłumaczenie tego na BF to:

[             # while a != 0:
    [->++<]       # b, a = a * 2, 0
    >[-<+>]       # a, b = b, 0
    <.            # print(a)
]

Pamiętaj jednak, że nie musimy być cały czas w tej samej pozycji podczas programu. Możemy pozwolić, aby wartość abyła tym, czym jesteśmy na początku każdej iteracji, a następnie mamy ten kod:

[             # while a != 0:
    [->++<]       # b, a = a * 2, 0
                  # implicitly let (a) be at the position of (b) now
    .             # print(a)
]

który jest kilka bajtów krótszy.


Ponadto zachowanie zawijania narożników również chroni mnie przed \lustrem - bez niego nie byłbym w stanie dopasować cyfr (+2 cyfry dla \siebie i +2 cyfry dla niesparowanego. po prawej stronie, nie wspominając o flagi)

(Detale:

  • Adres IP wchodzi do lewego dolnego rogu, kierując się w lewo
  • Został wypaczony w prawym rogu, wciąż kieruje się w lewo
  • Napotyka a \ co to odzwierciedla, teraz idzie prosto do góry
  • Wchodzi w róg i znów wypacza się w lewym dolnym rogu

)


Jeśli wartością (powyższej operacji mod 2) jest fałsz (zero), wówczas podążamy następującą ścieżką:

# Python                 # Hexagony   # Memory visualization after execution
b = mem // a             # :          # click here
base = ord('a') # 97     # a
y = b % base             # '%
offset = 33              # P1
z = y + offset           # ='+
stdout.write(chr(z))     # ;          # click here
mem = b // base          # {:         # click here

Nie wyjaśnię tutaj zbyt szczegółowo, ale przesunięcie nie jest właściwie dokładne 33, ale jest zgodne z 33modem 256. I chrma niejawny charakter % 256.


3
Człowieku, to dużo niepotrzebnych operacji
Jo King

26
Śmiałem się z „Aby zrozumieć, co mówię, posłuchajmy analogii [BrainFuck]”. Tylko na PPCG ... :)
Lynn

2
I przewijane jak 3 razy na górę odpowiedź na to upvote, tylko dowiedzieć się, że zrobiłem to już ...
NieDzejkob

2
310 bajtów , wykorzystując nową przestrzeń, skracając liczbę
Jo King

2
308 bajtów , zajmując jeszcze więcej miejsca
Jo King

46

Vim, 11 bajtów

q"iq"qP<Esc>hqP
  • iq"qP<Esc>: Ręcznie wstaw duplikat tekstu, który musi znajdować się poza nagraniem.
  • q"i hqP: Zapisz wnętrze bezpośrednio w ""rejestrze bez nazwy , aby można je było wkleić na środku. Jest hto jedyne wymagane repozycjonowanie; jeśli umieścisz go w makrze, zostanie wklejony do wyniku.

Edytować

Uwaga na temat nagrywania za pomocą q": Rejestr bezimienny ""jest zabawną rzeczą. To nie jest tak naprawdę rejestr, jak inne, ponieważ tam nie ma tekstu. W rzeczywistości jest to wskaźnik do innego rejestru (zwykle "-do usuwania bez nowej linii, "0do yanków lub "1do usuwania z nową linią). q"łamie zasady; tak naprawdę pisze "0. Jeśli ""wskazywałeś już na inny rejestr "0, q"nadpisze, "0ale pozostawi ""bez zmian. Kiedy zaczynasz świeżego Vima, ""automatycznie wskazuje na "0, więc w takim razie nic ci nie jest.

Zasadniczo Vim jest dziwny i pełen błędów.


poczekaj, dlaczego to mi nie działa
Destructible Lemon

@DestructibleWatermelon Nie mogę powiedzieć na pewno, ale jedno wyjaśnienie jest najbardziej prawdopodobne. Prawdopodobnie powinien był to wcześniej napisać, ponieważ może to zrzucić ludzi. Przeczytaj edycję.
udioica

powinieneś prawdopodobnie powiedzieć coś o tym, jak naciskanie ylub coś przed biegiem może pomóc
Destructible Lemon

Dlaczego nie używasz do pokazywania naciśnięcia klawisza <Esc>? Część tego „Kontrolnego
obrazu

4
@ mbomb007 <Esc>Notacja jest standardem w mapowaniach Vima ( :help <>) i właśnie tego używa vimgolf.com. Każdy doświadczony vimgolfer zostanie przyzwyczajony do czytania. Jeśli chodzi o Unicode, muszę zmrużyć oczy, aby przeczytać małe litery, a one zaciemniają metodę pisania ich i przeszukiwania pliku pomocy.
udioica

44

Cubix , 20 bajtów

3434Qu$v@!<"OOw\o;/"

Prawie dostałem \o/ ...

Netto :

    3 4
    3 4
Q u $ v @ ! < "
O O w \ o ; / "
    . .
    . .

Wypróbuj online

Wypróbuj tutaj !

Dodatkowe uwagi

Opowieść w tle

Po pod wrażeniem przeczytania tej świetnej odpowiedzi przez @ ais523, zacząłem myśleć o dalszym graniu w golfa. W końcu było tam sporo no-op, a to nie wydawało się bardzo skompresowane. Ponieważ jednak technika, której używa jego odpowiedź (i moja), wymaga, aby kod obejmował całe linie, potrzebna była oszczędność co najmniej 12 bajtów. W jego wyjaśnieniu była jedna uwaga, która sprawiła, że ​​pomyślałem:

Jeśli chodzi o grę w golfa w dół tego quina, [...] potrzebowałby [...] innego sposobu przedstawienia górnej powierzchni sześcianu [...]

Nagle, gdy wstałem i odszedłem po coś do picia, uderzyło mnie: co, jeśli program nie używałby kodów znaków, a raczej liczb reprezentujących górną twarz? Jest to szczególnie krótkie, jeśli drukowany numer ma 2 cyfry. Cubix posiada 3-bajtowych instrukcji jeden za popychanie numery dwucyfrowe: N, Si Q, które popychają 10, 32a34 odpowiednio, więc to powinno być dość Golfy, pomyślałem.

Pierwszą komplikacją związaną z tym pomysłem jest to, że górna twarz jest teraz wypełniona bezużytecznymi liczbami, więc nie możemy już tego używać. Drugą komplikacją jest to, że górna powierzchnia ma rozmiar, który jest kwadratem wielkości kwadratu, i musiał mieć parzysty rozmiar, w przeciwnym razie jedna liczba skończyłaby się również w pozycji początkowej wskaźnika instrukcji, prowadząc do zanieczyszczonego stosu. Z powodu tych komplikacji mój kod musiał zmieścić się na kostce wielkości 2 (która może zawierać „tylko” 24 bajty, więc musiałem grać w golfa co najmniej 21 bajtów). Ponieważ górne i dolne ściany są bezużyteczne, miałem tylko 16 bajtów efektywnych.

Zacząłem więc od wybrania liczby, która stanie się połową górnej części twarzy. Zacząłem od N(10), ale to nie do końca zadziałało z powodu podejścia, które podjąłem, aby wydrukować wszystko. Tak czy inaczej, zacząłem od nowa i Sz jakiegoś powodu użyłem (32). To dało właściwy quine, a przynajmniej tak mi się wydawało. Wszystko działało bardzo dobrze, ale brakowało cytatów. Potem przyszło mi do głowy, żeQ przyszło (34) będzie naprawdę przydatny. W końcu 34 to kod znakowy podwójnego cudzysłowu, który pozwala nam zachować go na stosie, oszczędzając (2, w stosowanym wówczas układzie) cenne bajty. Po tym, jak nieco zmieniłem trasę IP, pozostało mi tylko ćwiczenie, aby wypełnić puste pola.

Jak to działa

Kod można podzielić na 5 części. Przejrzę je jeden po drugim. Zauważ, że środkowe ściany kodujemy w odwrotnej kolejności, ponieważ model stosu jest wprowadzany jako ostatni na końcu.

Krok 1: Drukowanie górnej powierzchni

Nieistotne instrukcje zostały zastąpione przez no-ops ( .). IP rozpoczyna trzecią linię, po lewej stronie, skierowaną na wschód. Stos jest (oczywiście) pusty.

    . .
    . .
Q u . . . . . .
O O . . . . . .
    . .
    . .

IP kończy się na skrajnej lewej pozycji czwartej linii, wskazując na zachód, i ma zamiar zawinąć się do skrajnej prawej pozycji na tej samej linii. Wykonywane instrukcje to (bez znaku przepływu sterującego):

QOO
Q   # Push 34 (double quotes) to the stack
 OO # Output twice as number (the top face)

Stos zawiera tylko 34, reprezentujących ostatni znak źródła.

Krok 2: Zakoduj czwartą linię

Ten kawałek właściwie robi to, czego się spodziewasz: koduje czwartą linię. IP zaczyna się od podwójnego cudzysłowu na końcu tego wiersza i idzie na zachód, wypychając kody znaków każdego znaku, na którym wyląduje, aż znajdzie pasujące podwójne cudzysłowy. Ten pasujący podwójny cudzysłów jest także ostatnim znakiem w czwartym wierszu, ponieważ IP zawija się ponownie, gdy osiągnie lewą krawędź.

W efekcie adres IP przesunął się o jedną pozycję w lewo, a stos zawiera teraz reprezentację czwartej linii w kodach znaków i w odwrotnej kolejności.

Krok 3: Wciśnij kolejny cytat

Musimy przekazać kolejny cytat i czy jest lepszy sposób niż recykling Qna początku programu, podchodząc do niego z prawej strony? Ma to dodatkową zaletę, że adres IP bezpośrednio trafia do cytatu, który koduje trzecią linię.

Oto wersja netto dla tego kroku. Nieistotne intruzje zostały ponownie zastąpione przez no-ops, wykonywane no-op zostały zastąpione hashtagami ( #) w celach ilustracyjnych, a adres IP zaczyna się od ostatniego znaku w czwartym wierszu.

    . .
    . .
Q u $ . . . . .
. . w \ . . / .
    . #
    . #

Adres IP kończy się na trzeciej linii przy pierwszej instrukcji, która ma się owinąć na końcu tej linii, ponieważ wskazuje na zachód. Wykonano następujące instrukcje (z wyłączeniem przepływu kontrolnego):

$uQ
$u  # Don't do anthing
  Q # Push the double quote

Ten podwójny cytat reprezentuje ten na końcu trzeciego wiersza.

Krok 4: Kodowanie trzeciej linii

Działa to dokładnie tak samo jak w kroku 2, więc poszukaj tam wyjaśnienia.

Krok 5: Wydrukuj stos

Stos zawiera teraz czwartą i trzecią linię, w odwrotnej kolejności, więc wszystko, co musimy teraz zrobić, to wydrukować. IP zaczyna się od przedostatniej instrukcji na trzeciej linii, przesuwając się na zachód. Oto odpowiednia część kostki (ponownie, nieistotne części zostały zastąpione przez brak operacji).

    . .
    . .
. . . v @ ! < .
. . . \ o ; / .
    . .
    . .

Jest to pętla, jak można się było spodziewać / oczekiwać. Główny korpus to:

o;
o  # Print top of stack as character
 ; # Delete top of stack

Pętla kończy się, jeśli najwyższy element ma wartość 0, co dzieje się tylko wtedy, gdy stos jest pusty. Jeśli pętla się kończy, @wykonuje się, kończąc program.


szkoda, że ​​nie mogę jeszcze więcej
głosować

Nagrody są zawsze mile widziane ;-)
Łukasza

42

JavaScript ES6 - 21 bajtów

$=_=>`$=${$};$()`;$()

Nazywam to quine „Bling Quine”.

Czasami musisz grać w golfa w dobrym stylu.


Czy !$=_=>`!$=${$}()`()oszczędzasz 2 bajty?
Downgoat

Invalid assignment left hand side. Chciałbym, żeby to zadziałało :(
Mama Fun Roll

1
@ TùxCräftîñg eliminacja nawiasów wokół literałów szablonów działa tylko na natywne funkcje prototypowe, takie jak Array.prototype.join.
Mama Fun Roll

2
Hmm, nie jestem pewien. Napisałem to ponad rok temu (wtedy uważano to za ważne) i zbytnio nie śledziłem zmian zasad quine. Jednak dodanie alertlub console.logpo funkcji strzałki i zawijanie ciągu szablonu w nawiasach byłoby skuteczne.
Mama Fun Roll

3
Również jeśli uruchomisz to w konsoli, nadpisze ona $ (funkcja jQuery) na tej stronie, a funkcja upvote nie będzie już działać. :)
Steven Palinkas

41

Brainf * ck (755 znaków)

Jest to oparte na technice opracowanej przez Erika Bosmana (ejbosman at cs.vu.nl). Zwróć uwagę, że „ESultanik's Quine!” tekst jest rzeczywiście niezbędny, aby był quine!

->++>+++>+>+>++>>+>+>+++>>+>+>++>+++>+++>+>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>+>+>++>>>+++>>>>>+++>+>>>>>>>>>>>>>>>>>>>>>>+++>>>>>>>++>+++>+++>+>>+++>>>+++>+>+++>+>++>+++>>>+>+>+>+>++>+++>+>+>>+++>>>>>>>+>+>>>+>+>++>+++>+++>+>>+++>+++>+>+++>+>++>+++>++>>+>+>++>+++>+>+>>+++>>>+++>+>>>++>+++>+++>+>>+++>>>+++>+>+++>+>>+++>>+++>>>+++++++++++++++>+++++++++++++>++++++>+++++++++++++++>++++++++++>+++>+++>++++>++++++++++++++>+++>++++++++++>++++>++++++>++>+++++>+++++++++++++++>++++++++>++++>++++++++++++>+++++++++++++++>>++++>++++++++++++++>+++>+++>++++>++++++>+++>+++++++++>++++>+>++++>++++++++++>++++>++++++++>++>++++++++++>+>+++++++++++++++>+++++++++++++
ESultanik's Quine!
+[[>>+[>]+>+[<]<-]>>[>]<+<+++[<]<<+]>>+[>]+++[++++++++++>++[-<++++++++++++++++>]<.<-<]

13
To sprytny sposób na zrobienie tego.
Peter Olson

13
Jak to działa?
dumny haskeller

3
@proudhaskeller IIRC, część przed ESultanik's Quine!konfiguruje pamięć jako kodowanie stosu ESultanik's Quine!i dalej, z dwoma bajtami pamięci dla każdego znaku (przesunięcie wartości ASCII od 0x1F). Ostatni bit kodu zapętla się w pamięci, najpierw programowo odtwarzając ++>+++…kody dla każdego znaku, a następnie drukując znaki.
ESultanik,

4
@CatsAreFluffy Wymagane są, aby był to quine! Chociaż prawdą jest, że można je usunąć, należałoby również zmienić powyższy kod, aby zachować właściwość quine.
ESultanik,

1
To prawda. Konieczne są również nowe linie.
CalculatorFeline

36

Sześciokąt , długość boku 15 14 13 12, 616 533 456 383 bajtów

Po kilku dniach ostrożnej gry w golfa, przestawiania pętli i rozpoczynania od nowa, w końcu udało mi się sprowadzić do bocznego sześciokąta.

1845711724004994017660745324800783542810548755533855003470320302321248615173041097895645488030498537186418612923408209003405383437728326777573965676397524751468186829816614632962096935858"">./<$;-<.....>,.........==.........<"......."">'....>+'\.>.........==........<"......"">:>)<$=<..>..............$..<"...."">\'Q4;="/@>...............<"....."">P='%<.>.............<"..!'<.\=6,'/>

Wypróbuj online!

Rozłożony:

            1 8 4 5 7 1 1 7 2 4 0 0
           4 9 9 4 0 1 7 6 6 0 7 4 5
          3 2 4 8 0 0 7 8 3 5 4 2 8 1
         0 5 4 8 7 5 5 5 3 3 8 5 5 0 0
        3 4 7 0 3 2 0 3 0 2 3 2 1 2 4 8
       6 1 5 1 7 3 0 4 1 0 9 7 8 9 5 6 4
      5 4 8 8 0 3 0 4 9 8 5 3 7 1 8 6 4 1
     8 6 1 2 9 2 3 4 0 8 2 0 9 0 0 3 4 0 5
    3 8 3 4 3 7 7 2 8 3 2 6 7 7 7 5 7 3 9 6
   5 6 7 6 3 9 7 5 2 4 7 5 1 4 6 8 1 8 6 8 2
  9 8 1 6 6 1 4 6 3 2 9 6 2 0 9 6 9 3 5 8 5 8
 " " > . / < $ ; - < . . . . . > , . . . . . .
  . . . = = . . . . . . . . . < " . . . . . .
   . " " > ' . . . . > + ' \ . > . . . . . .
    . . . = = . . . . . . . . < " . . . . .
     . " " > : > ) < $ = < . . > . . . . .
      . . . . . . . . . $ . . < " . . . .
       " " > \ ' Q 4 ; = " / @ > . . . .
        . . . . . . . . . . . < " . . .
         . . " " > P = ' % < . > . . .
          . . . . . . . . . . < " . .
           ! ' < . \ = 6 , ' / > . .
            . . . . . . . . . . . .

Chociaż nie wygląda na najbardziej golfowy kod Hexagony, zastosowany przeze mnie rodzaj kodowania jest zoptymalizowany pod kątem dłuższych serii no-ops, czego w innym przypadku byś uniknął.

Wyjaśnienie

To bije poprzednią odpowiedź Hexagony , kodując no-ops ( .) w inny sposób. Podczas gdy ta odpowiedź oszczędza miejsce, czyniąc każdą inną postać a ., moja koduje liczbę braków operacji . Oznacza to również, że źródło nie musi być tak ograniczone.

Tutaj używam kodowanie base 80, gdzie numery poniżej 16 wskazują działa No-OPS, a numery od 16 do 79 stanowią szereg 32 ( !) do 95 ( _) (Ja tylko teraz realizującego ja grałem wszystkie _s z mojego kod lol). Niektóre pseudokod w języku Python:

i = absurdly long number
print(i)
base = 80
n = i%base
while n:
    if n < 16:
        print("."*(16-n))
    else:
        print(ASCII(n+16))
    i = i//base
    n = i%base

Liczba jest zakodowana w pierwszej połowie sześciokąta, wraz ze wszystkimi znakami

" " > 
 " " > 
  ... etc

po lewej stronie i

 > ,
< "
 >
< "
... etc

po prawej stronie przekierowując wskaźnik, aby zakodować liczbę w jednej komórce. To pochodzi z odpowiedzi Martina Endera (dzięki), ponieważ nie mogłem wymyślić bardziej efektywnego sposobu.

Następnie wchodzi do dolnej sekcji przez ->:

       " " > \ ' Q 4 ; = " / @ > . . . .
        . . . . . . . . . . . < " . . .
         . . " " > P = ' % < . > . . .
          . . . . . . . . . . < " . .
     ->    ! ' < . \ = 6 , ' / > . .

!wypisuje numer i 'przechodzi do właściwej komórki pamięci przed rozpoczęciem pętli. P='%modyfikuje bieżącą liczbę o 80. Jeśli wynikiem jest 0, przejdź do zakończenia @, w przeciwnym razie zejdź w dół i utwórz komórkę obok wyniku modyfikacji z wartością -16.

   . " " > ' . . . . > + ' \ . > . . . . . .
    . . . = = . . . . . . . . < " . . . . .
     . " " > : > ) < $ = < . . > . . . . .
      . . . . . . . . . $ . . < " . . . .
       " " > \ ' Q 4 ; = " / @ > . . . .
                      /
                     /

Ustaw komórkę na (wartość mod + -16). Jeśli ta wartość jest ujemna, przejdź na rozgałęzienie >+'\, w przeciwnym razie zejdź na dół.

Jeśli wartość jest dodatnia:

 " " > . / < $ ; - < . . . . . > , . . . . . .
  . . . = = . . . . . . . . . < " . . . . . .
   . " " > ' . . . . > + ' \ . > . . . . . .

Wskaźnik kończy się na tym, ;-<co ustawia komórkę na (wartość mod - -16) i drukuje ją.

Wartość jest ujemna:

   . " " > ' . . . . > + ' \ . > . . . . . .
    . . . = = . . . . . . . . < " . . . . .
     . " " > : > ) < $ = < . . > . . . . .

Zejdź do > ) <sekcji, która rozpoczyna pętlę. Tutaj jest izolowany:

     . . > ) < $ = < . .
      . . . . . . . . .
       \ ' Q 4 ; = " /

Który wykonuje kod, 'Q4;="=który wypisuje .(dzięki ponownie Martin Ender, który napisał program do znajdowania kombinacji liter i cyfr dla znaków) i wraca do początkowej komórki. Następnie zwiększa () ) komórkę wartości mod i zapętla ponownie, aż wartość mod będzie dodatnia.

Po wykonaniu tej czynności przesuwa się w górę i łączy z inną sekcją w:

 " " > . / < $ ; - < . . .
            \
             \

Wskaźnik ponownie wraca na początek większej pętli

 " " > . / <--
  . . . = =
   . " " > ' 
    . . . = = 
     . " " > :
      . . . . .
       " " > \ ' . .
        . . . . . . .
         . . " " > P = ' % < . > . . .

Wykonuje się, ='=:'która dzieli bieżącą liczbę przez 80 i przechodzi do właściwej komórki.

Stara wersja (długość boku 13)

343492224739614249922260393321622160373961419962223434213460086222642247615159528192623434203460066247203920342162343419346017616112622045226041621962343418346002622192616220391962343417346001406218603959366061583947623434"">/':=<$;'<.....>(......................<"......"">....'...>=\..>.....................<"....."">....>)<.-...>...........==......<"...."">.."...'.../>.................<"..."">\Q4;3=/.@.>...............<".."".>c)='%<..>..!'<.\1*='/.\""

Wypróbuj online!

Zdecydowanie mogę grać w golfa z innej strony, ale muszę to zostawić do jutra, bo robi się późno. Okazuje się, że jestem niecierpliwy i nie mogę się doczekać jutra. Może można grać w golfa z drugiej strony? :( ahhhhhhhh zrobiłem to!

Grałem nawet w kilka dodatkowych cyfr z kodowaniem bazowym 77, ale to naprawdę nie ma znaczenia, ponieważ ma tę samą liczbę bajtów.


13
To jest niesamowite. Pomysł na hybrydowe kodowanie przebiegów jest naprawdę fajny. :) Przypomnij mi, że dam ci nagrodę, jeśli zapomnę.
Martin Ender,

35

PostScript, 20 znaków

Krótki i legalny. 20 znaków, w tym końcowy znak nowej linii.

(dup == =)
dup == =

33

Cubix , 45 bajtów

.....>...R$R....W..^".<R.!'.\)!'"R@>>o;?/o'u"

Możesz przetestować ten kod tutaj .

Ten program jest dość trudny do naśladowania, ale aby mieć na to szansę, musimy zacząć od rozwinięcia go do kostki, tak jak robi to interpreter Cubix:

      . . .
      . . >
      . . .
R $ R . . . . W . . ^ "
. < R . ! ' . \ ) ! ' "
R @ > > o ; ? / o ' u "
      . . .
      . . .
      . . .

Jest to quine w stylu Befunge, która działa poprzez wykorzystanie zawijania, aby literały łańcuchowe „zawijały” kod wykonywalny (tylko z jednym " znakiem, kod jest jednocześnie wewnątrz i na zewnątrz cytatu, co staje się możliwe, gdy masz programy nieliniowe i nieplanarne). Zauważ, że pasuje to do naszej definicji właściwego quine, ponieważ dwa z podwójnych cudzysłowów nie kodują się same, ale raczej są obliczane później za pomocą arytmetyki.

Jednak w przeciwieństwie do Befunge używamy tutaj czterech ciągów zamiast jednego. Oto, w jaki sposób są wypychani na stos;

  1. Program rozpoczyna się u góry lewej krawędzi i idzie w prawo; skręca dwa razy w prawo ( R), co powoduje, że leci w lewo wzdłuż trzeciej i ostatniej linii otaczającej cały sześcian. Podwójny cudzysłów pasuje do siebie, więc wypychamy całą trzecią linię na stos do tyłu. Następnie wykonanie jest kontynuowane po podwójnym cytacie.

  2. uKomenda robi zawracania w prawo, więc następna rzecz, którą używasz jest z '"roku na środkowej linii. To popycha a "na stos. Kontynuując owijanie, uderzamy w <lewą stronę sześcianu i odbijamy się. Zbliżając się z tego kierunku, widzimy proste "polecenie, '"więc nie , więc cała druga linia jest wypychana na stos do tyłu powyżej trzeciej linii i podwójnego cudzysłowu.

  3. Zaczynamy od wpychania a !na stos ( '!) i zwiększania go ( )); powoduje to podwójny cudzysłów bez konieczności podwójnego cudzysłowu w naszym kodzie źródłowym (co mogłoby zakończyć ciąg znaków). Lustro ( \) odzwierciedla kierunek wykonywania w górę na północ; następnie Wpolecenie przesuwa się w lewo. To powoduje, że idziemy w górę siódmej kolumny, która ponieważ jest to sześcian, zawija się w lewo w trzecim rzędzie, a następnie w dół w trzeciej kolumnie. Trafiamy w R, skręcamy w prawo i idziemy w lewo wzdłuż górnego rzędu; następnie $przeskakuje Rprzez który weszliśmy do programu, więc wykonanie jest zawijane do "końca na końcu linii, i przechwytujemy pierwszą linię w ciągu znaków w taki sam sposób, jak zrobiliśmy to dla drugiej i trzeciej.

  4. ^Komenda wysyła nas na północ, aż do kolumny, która jest jedenastym (umożliwiającej owijania kostki) w kierunku południowym na piątą. Jedyne, co tam napotykamy !(pomiń, jeśli niezerowe; górna część stosu jest rzeczywiście niezerowa), które pomijają opolecenie, skutecznie powodując, że piąta kolumna jest całkowicie pusta. Wracamy więc do upolecenia, które ponownie zawraca, ale tym razem zostajemy w ostatniej kolumnie na południe, która zawija się do czwartej kolumny na północ. Jednak podczas zawracania trafiliśmy w podwójny cudzysłów, więc przechwytujemy całą czwartą kolumnę w ciągu, od dołu do góry. W przeciwieństwie do większości podwójnych cudzysłowów w programie, ten nie zamyka się; jest raczej zamknięty przez prawy "górny róg, co oznacza, że ​​przechwytujemy ciąg dziewięciu znaków ...>......

Tak więc układ stosu jest teraz, od góry do dołu: czwarta kolumna; Górny rząd; "; środkowy rząd; "; Dolny rząd. Każdy z nich jest reprezentowany na stosie, przy czym pierwszy znak znajduje się najbliżej góry stosu (Cubix popycha łańcuchy w odwrotnej kolejności, podobnie jak Befunge, ale za każdym razem, gdy IP porusza się w kierunku przeciwnym do naturalnego kierunku odczytu, więc zostało dwukrotnie odwrócone). Można zauważyć, że zawartość stosu jest prawie identyczna z oryginalnym programem (ponieważ czwarta kolumna i północna / górna ściana sześcianu zawierają te same znaki w tej samej kolejności; oczywiście tak zostało zaprojektowane celowo).

Następnym krokiem jest wydrukowanie zawartości stosu. Po wszystkich pchnięciach IP idzie w kierunku północnym w czwartej kolumnie, więc uderza >tam i wchodzi w ciasną pętlę >>o;?(tj. „Skręć na wschód, skręć na wschód, wyjdź jako postać, pop, skręć w prawo, jeśli jest dodatnia”). Ponieważ siódma linia jest pełna NOP, funkcja zwinie ?się z powrotem do pierwszej >, więc skutecznie wypycha całą zawartość stosu (? jest to brak operacji na pustym stosie). Prawie wydrukowaliśmy cały program! Niestety jeszcze nie zostało to zrobione; na końcu brakuje podwójnego cudzysłowu.

Po zakończeniu pętli odbijamy się od linii środkowej, przesuwając się na zachód, przez parę luster. ( \Wcześniej używaliśmy „drugiej strony” lustra; teraz używamy strony południowo-zachodniej. /Lustro nie było wcześniej używane.) Napotykamy '!, więc wciskamy wykrzyknik (tj. 33; używamy ASCII a Cubix nie rozróżnia liczb całkowitych i znaków) na stosie. (Dogodnie jest to to samo, !co owcześniej pominięte polecenie). Napotykamy parę Rpoleceń i używamy ich do wykonania „ręcznego” zawracania (drugie Rpolecenie zostało użyte wcześniej, aby dotrzeć do pierwszego wiersz, więc wydawało się najbardziej naturalne, aby dopasować inne polecenie, aby ominąć lewą stronę.R polecenie.W>polecenie w drugim wierszu, odbijając wykonanie dokładnie tam, gdzie było. Więc znów przeskakujemy w lewo, ale tym razem idziemy na południe, więc następnym poleceniem do wykonania jest )(inkrementacja wykrzyknika w podwójny cudzysłów), a następnie o(w celu wyjścia). Na koniec wykonanie jest zawijane wzdłuż ósmej linii do drugiej kolumny, gdzie znajduje się @wyjście z programu.

Przepraszam za zbłąkany apostrof w trzeciej linii. W tej wersji programu nic nie robi; była to część wcześniejszego pomysłu, który miałem, ale który okazał się niekonieczny. Jednak kiedy już dostałem działający quine, po prostu chciałem go przesłać, zamiast zepsuć go dalej, zwłaszcza że usunięcie go nie zmieniłoby liczby bajtów. Jeśli chodzi o dalszą grę w golfa, nie zaskoczyłoby mnie to, gdyby było to możliwe przy 3 × 3 tylko przy użyciu pierwszych pięciu linii, ale nie widzę oczywistego sposobu na zrobienie tego i musiałbym jeszcze ściślejsze upakowanie całego przepływu kontrolnego wraz z innym sposobem przedstawienia górnej powierzchni sześcianu (lub modyfikacją algorytmu, aby mógł nadal używać czwartej kolumny, nawet jeśli miałby teraz dziesięć lub jedenaście znaków) .


Dobra robota, to naprawdę imponujący wynik. Uwielbiam sposób, w jaki zakodowałeś górną twarz. :)
Martin Ender,

To jest po prostu niesamowite! Jeśli to pomoże każdy, inny sposób do pchania "jest Q.
ETHproductions

1
Łał! Nigdy nie myślałem, że zobaczę quine cubix!
FlipTack,

3
Nie miałem czasu wczoraj przeczytać wyjaśnienia, ale teraz, kiedy mam ... Po prostu ... WOW. Nie mogę uwierzyć, ile znaków jest używanych do dwóch, a nawet trzech zupełnie różnych celów. To prawdopodobnie najfajniejszy program Cubix, jaki kiedykolwiek widziałem.
ETHproductions

Dobre wytłumaczenie.
Robert Fraser

33

Python 2, 30 bajtów

_='_=%r;print _%%_';print _%_

Zabrano stąd


1
+1, pobiłeś moje podobne rozwiązanie, więc je usunąłem. Należy zauważyć, że działa to tylko w Pythonie 2.
nyuszika7h

2
Wygląda dziwnie z nazwą zmiennej jako _, ale brzmi lepiej, jeśli przypiszesz ją do dowolnej litery, tzn. S:s='s=%r;print s%%s';print s%s
Ehtesh Choudhury

5
Jeśli to rozwiązanie nie jest tworem własnym, powinieneś uczynić z niego Wiki Wiki. Link nie działa.
mbomb007 27.04.16

1
Jestem trochę spóźniony na imprezę, ale czy ktoś może wyjaśnić, jak to działa?
MadTux,

9
Wymaga to podania końcowego przewodu. W tej chwili kod źródłowy nie pasuje do wyniku.
Dennis

32

Vim, 17 , 14 naciśnięć klawiszy

Ktoś losowo to ocenił, więc przypomniałem sobie, że istnieje. Kiedy go ponownie przeczytałem, pomyślałem: „Hej, mogę zrobić coś więcej!”, Więc oderwałem dwa bajty. To wciąż nie jest najkrótszy, ale przynajmniej poprawa.


Przez długi czas zastanawiałem się, czy możliwe jest użycie vim quine. Z jednej strony musi być to możliwe, ponieważ vim jest już gotowy. Ale po długim poszukiwaniu vim quine nie byłem w stanie go znaleźć. I nie uważają tego PPCG wyzwanie , ale jest zamknięty i nie dokładnie o dosłowne quines. Zdecydowałem się na taki, ponieważ nie mogłem go znaleźć.

Jestem naprawdę dumny z tej odpowiedzi z dwóch pierwszych powodów :

  1. To pierwszy quine, jaki kiedykolwiek stworzyłem

  2. O ile mi wiadomo, to pierwsza na świecie publikacja vim-quine ! Mogę się mylić w tej sprawie, więc jeśli znasz jedną, daj mi znać.

Po tym długim wprowadzeniu oto:

qqX"qpAq@q<esc>q@q

Wypróbuj online!

Pamiętaj, że po wpisaniu tego <esc>klawisza wyświetli się jako ^[. Jest to nadal dokładne, ponieważ ^[reprezentuje 0x1B, co jest ucieczką w ASCII , a sposób, w jaki vim wewnętrznie reprezentuje <esc>klucz.

Zauważ również , że testowanie to może się nie powieść, jeśli załadujesz istniejącą sesję vim. Napisałem odpowiedzieć wyjaśniając, że tutaj , jeśli chcesz uzyskać więcej informacji, ale przede wszystkim trzeba uruchomić z vim

vim -u NONE -N -i NONE

lub wpisz qqqprzed uruchomieniem tego.

Wyjaśnienie:

qq                  " Start recording into register 'q'
  X                 " Delete one character before the cursor (Once we play this back, it will delete the '@')
   "qp              " Paste register 'q'
      Aq@q<esc>     " Append 'q@q' to this line
               q    " Stop recording
                @q  " Playback register 'q'

Na marginesie, ta odpowiedź jest prawdopodobnie rekordem świata dla większości q w odpowiedzi PPCG lub coś w tym rodzaju.


1
2i2i<esc>jest tak blisko. Czuję, że musi być coś, co mogę zrobić, aby to zadziałało.
Zwei

@zwei Wiem, jest blisko to boli! Właściwie <Esc>jest ukryty w V, więc to działa . Niestety dodaje również nowy wiersz, dlatego jeszcze go nie opublikowałem.
DJMcMayhem

q"iq"qbP<Esc>qbPma 11. Po umieszczeniu tego na reddit , zbadałem tutaj vimgolfing i postanowiłem założyć konto. Oto odpowiedź, którą tam zamieściłem.
udioica

2
@udioica Czy możesz to opublikować jako odpowiedź?
DJMcMayhem

28

utracone , 120 116 98 96 76 70 66 bajtów

Edycja: tak, poniżej 100

Edycja: Zapisano kilka bajtów, przełączając na wszystkie /s w dolnym wierszu

:2+52*95*2+>::1?:[:[[[[@^%?>([ "
////////////////////////////////

Wypróbuj online! + weryfikacja jest deterministyczna dla wszystkich możliwych stanów

Lost to język 2D, w którym pozycja początkowa i kierunek są całkowicie losowe. Oznacza to, że na każdym etapie musi być dużo sprawdzania błędów, aby upewnić się, że masz prawidłowy wskaźnik instrukcji, i nie jest to taki, który właśnie wędrował losowo.

Wyjaśnienie:

Wszystkie /s w dolnej linii są tam, aby upewnić się, że wszystkie wskaźniki, które spawnują się w kierunku pionowym lub w dolnej linii, zostaną umieszczone we właściwym kierunku. Stamtąd kończą w kilku różnych miejscach, ale wszystkie trafiają prosto do

 ^%?>
 ////

Który usuwa wszystkie niezerowe liczby ze stosu. The([Potem czyści żadnych dodatkowych 0s również.

W środku klarowania uderza w %, co wyłącza „bezpieczeństwo”, co pozwala programowi zakończyć się, gdy trafi @(bez tego program mógłby zakończyć się natychmiast, jeśli wskaźnik uruchomi się na@ ).

Stamtąd robi dość prosty quine język 2D, owijając literał ciąg ( ") wokół pierwszego wiersza, popychając "znak, kopiując spację ( :2+), a następnie nową linię ( 52*). W drugim wierszu tworzy /znak ( 95*2+) i powiela go pęczek ( >::1?:[:[[[[), zanim ostatecznie kończy się na @i niejawnie drukuje stos. Ma ?1to na celu powstrzymanie procesu tworzenia zbyt wielu zer, jeśli wskaźnik wejdzie wcześnie, oszczędzając na konieczności ich późniejszego usunięcia.

Zapisałem tutaj 20 bajtów, czyniąc ostatni wiersz tym samym znakiem, co oznacza, że ​​mogłem przejść od procesu kopiowania do końca @.

Objaśnienie procesu kopiowania:

[to postać znana jako „drzwi”. Jeśli wskaźnik uderza w płaską stronę a [lub a ], odbija się, w przeciwnym razie przechodzi przez niego. Za każdym razem, gdy wskaźnik wchodzi w interakcje z drzwiami, zmienia się na przeciwny typ. Korzystając z tej wiedzy, możemy skonstruować prosty wzór na to, ile razy instrukcja wykona się w >:[bloku.

Dodaj początkową liczbę instrukcji. Do każdego [dodaj 2 razy więcej instrukcji po lewej stronie. Na przykład >::::[:[[[zaczynamy od 5 jako kwoty początkowej. Pierwsze drzwi mają 4 instrukcje dupe, więc dodajemy 4 * 2 = 8 do 5, aby uzyskać 13. Pozostałe trzy drzwi mają 5 duplikatów po lewej stronie, więc dodajemy 3 * (5 * 2) = 30 do 13, aby uzyskać 43 wykonane instrukcje dupe i mają 44 >s na stosie. Ten sam proces można zastosować do innych instrukcji, takich jak( wypychanie dużej liczby przedmiotów ze stosu do lunety lub, jak tutaj zastosowano, do usuwania przedmiotów ze stosu.

Sztuczka, której użyłem tutaj, aby uniknąć kopiowania zbyt wielu zer, to 1?. Jeśli znak ma wartość 0, ?nie pomija 1, co oznacza, że ​​duplikuje 1 przez pozostałą część dupe. To znacznie ułatwia późniejsze wyczyszczenie stosu.


25

Są to dwie najkrótsze rubinowe quiny z SO :

_="_=%p;puts _%%_";puts _%_

i

puts <<2*2,2
puts <<2*2,2
2

Nie pytaj mnie, jak działa ten drugi ...


8
Drugi używa heredoc, <<2rozpoczyna ciąg w następnym wierszu i *2powtarza ciąg
Ming-Tang

Dlaczego potrzebujesz 2?
CalculatorFeline

1
@CalculatorFeline Jest to terminator łańcucha heredoc (który musi pojawić się we własnej linii). W rzeczywistości nie musi to być 2: tio.run/##KypNqvz/v6C0pFjBxsZAy0jHgAuFY8D1/z8A
Martin Ender

25

Rozszczepienie , 6 bajtów

Wygląda na to, że jest to obecnie najkrótszy „właściwy” quine spośród tych odpowiedzi.

'!+OR"

Wyjaśnienie

Przepływ kontrolny zaczyna się Rod pojedynczego prawego (1,0)atomu. Uderza w "tryb przełączania, a następnie owija się wokół linii, drukując '!+ORprzed ponownym naciśnięciem tego samego "i wychodzeniem z trybu drukowania.

To pozostawia "się do wydrukowania. Najkrótsza droga to '"O(gdzie '"ustawia masę atomu na kod znaku "i Odrukuje znak i niszczy atom), ale jeśli to "zrobilibyśmy, to zakłócałoby tryb drukowania. Zamiast tego ustawiamy wartość atomu na '!(jeden mniej niż "), następnie zwiększamy za pomocą, +a następnie drukujemy wynik za pomocą O.

Alternatywy

Oto kilka alternatyw, które są dłuższe, ale może ich techniki zainspirują kogoś do znalezienia krótszej wersji, która je wykorzysta (a może będą bardziej przydatne w niektórych uogólnionych quinach).

8 bajtów przy użyciu Jump

' |R@JO"

Ponownie kod zaczyna się od R. @Masa swap, energia dać (0,1). Dlatego Jsprawia, że ​​atom przeskakuje Oprosto na ". Następnie, jak poprzednio, wszystkie oprócz tych "są drukowane w trybie ciągów. Następnie atom uderza, |aby odwrócić swój kierunek, a następnie przechodzi przez '"Odrukowanie ". Przestrzeń jest nieco denerwująca, ale wydaje się konieczna, ponieważ w przeciwnym razie 'atom potraktowałby atom |jak postać zamiast lustra.

8 bajtów przy użyciu dwóch atomów

"'L;R@JO

Ma dwa atomy, zaczynając od lewej i od Lprawej R. Lewostronny atom otrzymuje swoją wartość, dzięki '"której jest natychmiast drukowany za pomocą O(i atom jest niszczony). Dla właściwego atomu ponownie zamieniamy masę i energię, przeskakujemy nad, Oaby wydrukować resztę kodu w trybie drukowania. Następnie jego wartość jest ustawiana przez, 'Lale to nie ma znaczenia, ponieważ atom jest następnie odrzucany za pomocą ;.


Technicznie niepoprawny z powodu braku separacji kodu / danych w źródle.
CalculatorFeline

4
@CalculatorFeline '!+koduje ".
Martin Ender

Nie znam Fission, ale |R@JO"'zadziałałoby, czy nadal potrzebowałbyś tego miejsca po '?
Łagodnie Milquetoast

1
@MistahFiggins Myślę, że tak, ale co ważniejsze, wydrukujesz 'pierwszy.
Martin Ender,

24

JavaScript w przeglądarce (41 znaków)

Działa w 5 najlepszych przeglądarkach internetowych (IE> = 8, Mozilla Firefox, Google Chrome, Safari, Opera). Wpisz go do konsoli programisty w jednym z poniższych:

eval(I="'eval(I='+JSON.stringify(I)+')'")

To nie jest „oszustwo” - w przeciwieństwie do jednobajtowego quina Chrisa Jester-Younga, ponieważ można go łatwo zmodyfikować, aby używał tej alert()funkcji (kosztuje 14 znaków):

alert(eval(I="'alert(eval(I='+JSON.stringify(I)+'))'"))

Lub przekształcony w bookmarklet (kosztuje 22 znaki):

javascript:eval(I="'javascript:eval(I='+JSON.stringify(I)+')'")

24

C, 64 60 bajtów

main(s){printf(s="main(s){printf(s=%c%s%1$c,34,s);}",34,s);}

Jak dotąd jest to najkrótsza znana quina C. Tam jest rozszerzony Bounty jeśli okaże się krótsza.

Działa to w GCC , Clang i TCC w środowisku POSIX . W przypadku wszystkich z nich wywołuje nadmierną liczbę niezdefiniowanych zachowań.

Dla zabawy, oto repozytorium zawierające wszystkie znane mi litery C. Zachęcamy do rozwidlenia / PR, jeśli znajdziesz lub napiszesz inny, który doda coś nowego i kreatywnego w stosunku do istniejących.

Pamiętaj, że działa tylko w środowisku ASCII . To działa dla EBCDIC , ale nadal wymaga POSIX . Powodzenia w znalezieniu środowiska POSIX / EBCDIC: P


Jak to działa:

  1. main(s)nadużywa mainargumentów, deklarując zmienną praktycznie bez typus . (Pamiętaj, że stak naprawdę nie jest to bez typu, ale ponieważ wymienione kompilatory automatycznie rzutują go w razie potrzeby, równie dobrze może być *).
  2. printf(s="..." zestawy s podany ciąg i przekazuje pierwszy argument do printf.
  3. sjest ustawiony na main(s){printf(s=%c%s%1$c,34,s);}.
  4. %cJest ustawione na ASCII 34, ". To umożliwia quine. Teraz swygląda następująco:
    main(s){printf(s="%s%1$c,34,s);} .
  5. %sJest ustawiony na ssobie, co jest możliwe dzięki # 2. Teraz swygląda następująco:
    main(s){printf(s="main(s){printf(s=%c%s%1$c,34,s);}%1$c,34,s);} .
  6. %1$cJest ustawione na ASCII 34 ", printf„s ** pierwszy argument. Teraz swygląda to tak:
    main(s){printf(s="main(s){printf(s=%c%s%1$c,34,s);}",34,s);}
    ... tak się składa, że ​​jest to oryginalny kod źródłowy.

* Przykład dzięki @Pavel
** pierwszy argument po specyfikacją formatu - w tym przypadku s. Odwołanie do specyfikatora formatu jest niemożliwe.


Myślę, że to niemożliwe, żeby to samo się skróciło. Gdyby printfspecyfikator formatu był dostępny przez $, działałoby to dla 52 bajtów:

main(){printf("main(){printf(%c%0$s%1$c,34);}",34);}

Chociaż z pewnością nie powinno się to zaliczać do konkurencji, zwycięzca „Najgorszego nadużycia zasad” z Międzynarodowego Konkursu Obfuscated C Code 1994, 1994_smr.c , jest zdecydowanie krótszy.
Ray

@ Prom nie jest dozwolone. Z definicji nie jest to właściwy quine. Zasady quien zostały zmienione z powodu tego programu: P
MD XF

Zgadzam się całkowicie, ale jest to wystarczająco interesujący hack, o którym warto wspomnieć za każdym razem, gdy ktoś wspomina o najmniejszym znanym quine, choćby z powodów historycznych.
Ray

4
sjest typu int, a nie „zmienną bez typu”.
feersum

2
Wszystkie te kompilatory najwyraźniej umożliwiają niejawną konwersję wskaźnika na int. s=3oczywiście nie zadziałałoby, ponieważ musisz dwukrotnie przekazać ciąg printf.
feersum

24

Java, 528 bajtów:

Rozwiązanie Java z oryginalnym podejściem:

import java.math.*;class a{public static void main(String[]a){BigInteger b=new BigInteger("90ygts9hiey66o0uh2kqadro71r14x0ucr5v33k1pe27jqk7mywnd5m54uypfrnt6r8aks1g5e080mua80mgw3bybkp904cxfcf4whcz9ckkecz8kr3huuui5gbr27vpsw9vc0m36tadcg7uxsl8p9hfnphqgksttq1wlolm2c3he9fdd25v0gsqfcx9vl4002dil6a00bh7kqn0301cvq3ghdu7fhwf231r43aes2a6018svioyy0lz1gpm3ma5yrspbh2j85dhwdn5sem4d9nyswvx4wmx25ulwnd3drwatvbn6a4jb000gbh8e2lshp",36);int i=0;for(byte c:b.toByteArray()){if(++i==92)System.out.print(b.toString(36));System.out.print((char)c);}}}

w czytelnej formie:

import java.math.*;
class a
{
    public static void main (String [] a)
    {
        BigInteger b=new BigInteger ("90ygts9hiey66o0uh2kqadro71r14x0ucr5v33k1pe27jqk7mywnd5m54uypfrnt6r8aks1g5e080mua80mgw3bybkp904cxfcf4whcz9ckkecz8kr3huuui5gbr27vpsw9vc0m36tadcg7uxsl8p9hfnphqgksttq1wlolm2c3he9fdd25v0gsqfcx9vl4002dil6a00bh7kqn0301cvq3ghdu7fhwf231r43aes2a6018svioyy0lz1gpm3ma5yrspbh2j85dhwdn5sem4d9nyswvx4wmx25ulwnd3drwatvbn6a4jb000gbh8e2lshp", 36); 
        int i=0; 
        for (byte c:b.toByteArray ())
        {
            if (++i==92) 
                System.out.print (b.toString (36)); 
            System.out.print ((char) c);
        }
    }
}

Jak to działa?
Loovjo

1
@Loovjo: Podobnie jak inne rozwiązania, które przecinają kod na dwie części i wstawiają cały ciąg znaków, który ponownie przedstawia kod wewnątrz, ale cały kod nie jest tylko ciągiem, ale jest zakodowany jako długa liczba w podstawie 36 (26 znaków alfabetycznych + 10 cyfry).
użytkownik nieznany

1
Można to skrócić, jeśli się położy if(++i==92),
tuskiomi

2
@tuskiomi: Dzięki, skrócono o dwa znaki
użytkownik nieznany

1
@ userunknown W rzeczywistości, a*ponieważ tablica nie wychodzi z Javy, to jest C. Niektóre inne elementy golfa: import java.math.*;class a{public static void main(String[]a){BigInteger b=new BigInteger("abc",36);int i=0;for(int c:b.toByteArray())System.out.printf("%s%c",++i==92?b.toString(36):"",c);}}gdzie abcbyłaby nowo obliczona magiczna liczba String. W Javie 8+ jest to również możliwe, aby zmienić class a{public static void mainsię interface a{static void main, aw Java 10+ jest to również możliwe, aby zmienić import java.math.*;i BigInteger b=new BigInteger(do var b=new java.math.BigInteger(.
Kevin Cruijssen

23

Kurczak , 7

chicken

Nie, to nie jest bezpośrednio powtarzane :)


Cholera, pobiłeś mnie do tego :)
Taconut

To nie echo, to struna chicken!
Erik the Outgolfer

Brak separacji kodu / danych, dlatego jest nieprawidłowy.
CalculatorFeline

10
@CalculatorFeline Czy czytałeś zasady?
Timtech,

1
@JoKing Nie sądzę, że jest to nieprawidłowe, ponieważ reguły wyzwania zabraniają tylko zerowej długości i oszukiwania (czytania własnego pliku źródłowego). Jedyną rzeczą, która zabrania niewłaściwych quinesów, jest standardowa luka - z wyjątkiem tych, które zwykle nie są uważane za mające zastosowanie do odpowiedzi poprzedzających je.
pppery

23

Siatkówka , 20 14 9 7 bajtów

Zanim zaczniemy, chciałbym wspomnieć o trywialnym rozwiązaniu pliku, który zawiera jeden plik 0. W takim przypadku Retina spróbuje policzyć 0s na pustym wejściu, czego wynikiem jest również0 . Nie uważałbym jednak tego za dobry quine.

Oto właściwy:

>\`
>\`

Wypróbuj online!

Alternatywnie, moglibyśmy użyć ;zamiast >.

Wyjaśnienie

Program składa się z jednego zamiennika, który drukujemy dwukrotnie.

W pierwszym wierszu ` separuje konfigurację od wyrażenia regularnego, więc wyrażenie jest puste. Dlatego pusty ciąg (tj. Nieistniejące wejście) jest zastępowany drugim wierszem, dosłownie.

Aby wydrukować wynik dwukrotnie, zawijamy go w dwa etapy wyjściowe. Wewnętrzny \drukuje wynik z końcowym podawaniem linii, a zewnętrzny,> drukuje go bez niego.

Jeśli jesteś trochę zaznajomiony z Retiną, możesz zastanawiać się, co się stało z dorozumianymi wynikami Retiny. Domniemane wyjście Retiny polega na zawinięciu ostatniego etapu programu w etap wyjściowy. Jednak Retina tego nie robi, jeśli ostatni etap jest już etapem wyjściowym. Powodem tego jest to, że w normalnym programie bardziej użyteczna jest możliwość zastąpienia domyślnego stopnia wyjściowego specjalnym stopniem podobnym \lub ;pojedynczym bajtem (zamiast konieczności pozbycia się domyślnego stopnia z .flagą). Niestety takie zachowanie kosztuje nas dwa bajty na quine.


20

JavaScript (36 znaków)

(function a(){alert("("+a+")()")})()

To jest AFAICT, najkrótsza jak dotąd napisana javascript.


1
To ... robi wrażenie. Powinieneś wyjaśnić, jak to działa dla mnie 8- |
TehShrike 27.09.11

3
@TehShrike Wskazówka: możesz wyświetlić zawartość funkcji, zmuszając ją do łańcucha. Na przykład, jeśli masz funkcję a, możesz uzyskać dostęp do jej zawartości przez wywołanie a.toString.
Peter Olson,

7
Aby być pedantycznym, jest to tylko quine, jeśli twoja implementacja JavaScript strunkuje funkcję adokładnie w taki sam sposób, jak napisano powyżej. Jednak dane wyjściowe tego kodu mogą być quine w każdej implementacji JavaScript.
Ilmari Karonen

1
Oto sam Quine, 1 bajt krócej: !function a(){alert("!"+a+"()")}().
Ismael Miguel

1
(a=()=>alert(({a})))()
Dennis C

19

GolfScript, 8 bajtów

Zawsze myślałem, że najkrótsza (prawdziwa) Quine GolfScript ma 9 bajtów:

{'.~'}.~

Tam, gdzie konieczne jest końcowe podawanie linii, ponieważ GolfScript domyślnie drukuje końcowe podawanie linii.

Ale właśnie znalazłem 8-bajtowy quine, który działa dokładnie wokół tego ograniczenia wysuwu linii:

":n`":n`

Wypróbuj online!

Więc haczyk polega na tym, że GolfScript nie drukuje końcowego przesuwu linii, ale drukuje zawartość nna końcu programu. Po prostu nzawiera on źródło na początek. Pomysł polega więc na zastąpieniu go łańcuchem ":n`", a następnie jego usztywnieniu, tak aby kopia na stosie była drukowana z cytatami i kopią przechowywaną na nodcinkach bez.

Jak zauważył Thomas Kwa, 7-bajtowy quine CJam można również dostosować do 8-bajtowego rozwiązania:

".p"
.p

Znowu potrzebujemy końcowego przewodu.


6
Gra w golfa jest dziwna.
CalculatorFeline

19

Labirynt , 124 110 53 bajtów

Dzięki Sp3000 za grę w golfa z 9 bajtów, co pozwoliło mi grać w golfa z kolejnymi 7.

44660535853919556129637653276602333!
1
:_98
/8 %
@9_.

Wypróbuj online!

Wyjaśnienie

Labirynt 101:

  • Labirynt to język 2D oparty na stosie. Stos jest bezdenny i wypełniony zerami, więc wyskakiwanie z pustego stosu nie jest błędem.
  • Wykonanie rozpoczyna się od pierwszego ważnego znaku (tutaj w lewym górnym rogu). Na każdym skrzyżowaniu, gdzie istnieją dwie lub więcej możliwych ścieżek, które ma wziąć wskaźnik instrukcji (IP), sprawdzana jest góra stosu, aby określić, gdzie iść dalej. Negatyw to skręt w lewo, zero to przejście do przodu, a dodatnie to skręt w prawo.
  • Cyfry w kodzie źródłowym nie wypychają odpowiedniej liczby - zamiast tego wyskakują na wierzch stosu i pchają n*10 + <digit>. Pozwala to na łatwe budowanie dużych liczb. Aby rozpocząć nowy numer, użyj _, który wypycha zero.
  • " nie ma operacji.

Najpierw wyjaśnię nieco prostszą wersję, która jest dłuższa, ale trochę mniej magiczna:

395852936437949826992796242020587432!
"
:_96
/6 %
@9_.

Wypróbuj online!

Główną ideą jest zakodowanie głównej części źródła w jednym numerze, z wykorzystaniem dużej bazy. Numer ten można następnie łatwo wydrukować, zanim zostanie zdekodowany w celu wydrukowania pozostałej części kodu źródłowego. Dekodowanie jest po prostu powtórzeniem aplikacji divmod base, w której wypisuje modi kontynuuje pracę z do divdo zera.

Unikając tego {}, najwyższy potrzebny nam kod znaków to _(95), tak że podstawa 96 jest wystarczająca (utrzymując bazę na niskim poziomie, liczba na początku jest krótsza). Więc chcemy zakodować to:

!
"
:_96
/6 %
@9_.

Przekształcając te znaki w ich punkty kodowe i traktując wynik jako liczbę podstawową 96 (z najmniej znaczącą cyfrą odpowiadającą !i najbardziej znaczącą do ., ponieważ jest to kolejność, w jakiej rozłożymy liczbę), otrzymujemy

234785020242697299628949734639258593

Teraz kod zaczyna się od całkiem fajnej sztuczki (jeśli mogę tak powiedzieć), która pozwala nam wydrukować kodowanie z powrotem i zachować kolejną kopię do dekodowania z niewielkim narzutem: wstawiamy liczbę do kodu w odwrotnej kolejności. Obliczyłem wynik za pomocą tego skryptu CJam Przejdźmy więc do właściwego kodu. Oto początek:

395852936437949826992796242020587432!
"

Adres IP zaczyna się w lewym górnym rogu i idzie na wschód. Przesuwając te cyfry, po prostu gromadzi tę liczbę na wierzchu stosu. Sama liczba jest całkowicie bez znaczenia, ponieważ jest odwrotnością tego, czego chcemy. Gdy adres IP trafi do !, wyskakuje ten numer ze stosu i drukuje go. To wszystko, aby odtworzyć kodowanie na wyjściu.

Ale teraz IP dotarło w ślepy zaułek. Oznacza to, że odwraca się i teraz wraca na zachód (bez !ponownego wykonywania ). Tym razem, dogodnie, adres IP odczytuje liczbę od tyłu do przodu, tak więc teraz robi to liczba na górze stosu kodować resztę źródła.

Kiedy IP teraz znów uderza w lewy górny róg, nie jest to ślepy zaułek, ponieważ IP może skręcić w lewo, więc robi to i teraz przesuwa się na południe. "Jest no-op, że musimy tu oddzielić od liczby pętli głównej kodeksu. A propos:

...
"
:_96
/6 %
@9_.

Dopóki górna część stosu nie jest jeszcze równa zero, adres IP będzie przebiegał przez ten raczej gęsty kod w następującej pętli:

"
>>>v
^< v
 ^<<

Lub ułożone liniowo:

:_96%._96/

Powodem, dla którego zabiera te zakręty, jest semantyka sterowania przepływem Labiryntu. Gdy w bieżącej komórce znajduje się co najmniej trzech sąsiadów, IP skręci w lewo na ujemną wartość stosu, przejdź do zera i skręci w prawo na dodatnią wartość stosu. Jeśli wybrany kierunek nie jest możliwy ze względu na ścianę, IP przyjmie zamiast tego kierunek przeciwny (dlatego w kodzie są dwa zakręty w lewo, chociaż góra stosu nigdy nie jest ujemna).

Sam kod pętli jest właściwie bardzo prosty (kompresowanie go tak ściśle nie było i jest to, gdzie główny wkład Sp3000 jest):

:    # Duplicate the remaining encoding number N.
_96  # Push 96, the base.
%.   # Take modulo and print as a character.
_96  # Push 96 again.
/    # Divide N by 96 to move to the next digit.

Po osiągnięciu Nzera zmienia się przepływ kontrolny. Teraz IP chciałby iść prosto za /(tj. Na zachód), ale tam jest ściana. Zamiast tego, jeśli odwróci się (na wschód), wykonuje 6ponownie. To sprawia, że ​​górna część stosu jest dodatnia, więc IP skręca w prawo (południe) i wykonuje 9. Szczyt stosu jest teraz 69, ale zależy nam tylko na tym, aby był pozytywny. IP wykonuje kolejny zakręt w prawo (na zachód) i przesuwa się na@ który kończy kod.

W sumie całkiem proste.

Okej, teraz jak golimy ten dodatkowy bajt. Oczywiście ten brak operacji wydaje się marnotrawstwem, ale potrzebujemy tego dodatkowego wiersza: jeśli pętla przylegałaby do liczby, adres IP już by się tam przeniósł zamiast przemieścić cały numer. Czy możemy zrobić coś przydatnego z tym brakiem operacji?

Zasadniczo możemy tego użyć, aby dodać ostatnią cyfrę do kodowania. Kodowanie tak naprawdę nie musi być w pierwszej linii ... po !prostu zapewnia, że ​​cokolwiek jest tam , również zostanie wydrukowane.

Jest jednak pewien haczyk, nie możemy tego po prostu zrobić:

95852936437949826992796242020587432!
3
:_96
/6 %
@9_.

Problem polega na tym, że teraz zmieniliśmy na "a 3, co również zmienia faktyczną liczbę, którą chcemy mieć. I na pewno ta liczba się nie kończy 3. Ponieważ liczba jest całkowicie określana przez kod zaczynający się od !, nie możemy wiele z tym zrobić.

Ale może możemy wybrać inną cyfrę? Tak naprawdę nie dbamy o to, czy jest 3w tym miejscu, o ile skończymy z liczbą, która poprawnie koduje źródło. Niestety, żadna z 10 cyfr nie daje kodowania, którego najmniej znacząca cyfra odpowiada wybranemu. Na szczęście w pozostałej części kodu jest trochę swobody, dzięki czemu możemy wypróbować jeszcze kilka kodowań bez zwiększania liczby bajtów. Znalazłem trzy opcje:

  1. Możemy zmienić @na /. W takim przypadku możemy użyć dowolnej cyfry 1357i uzyskać pasujące kodowanie. Oznaczałoby to jednak, że program kończy działanie z błędem, który jest dozwolony, ale nie wydaje się bardzo czysty.
  2. Spacje nie są jedynymi „ścianami”. Każda nieużywana postać to w szczególności wszystkie litery. Jeśli użyjemy dużej litery, nie musimy nawet zwiększać bazy, aby ją dostosować (ponieważ te punkty kodowe są poniżej _). 26 wyborów daje wiele możliwości. Np. DlaA dowolnej cyfry nieparzystej działa. Jest to nieco ładniejsze, ale nadal nie wydaje się aż tak eleganckie, ponieważ nigdy nie użyłbyś tam litery w prawdziwym kodzie.
  3. Możemy użyć większej bazy. Dopóki nie zwiększymy znacząco bazy, liczba cyfr dziesiętnych w kodowaniu pozostanie taka sama (w szczególności każda podstawa do 104 jest w porządku, chociaż podstawy powyżej 99 faktycznie wymagałyby dodatkowych znaków w samym kodzie). Na szczęście baza 98 daje jedno pasujące rozwiązanie: kiedy używamy cyfry 1, kodowanie również się kończy 1. Jest to jedyne rozwiązanie wśród baz 96, 97, 98, 99, więc jest to naprawdę bardzo szczęśliwe. W ten sposób otrzymujemy kod u góry tej odpowiedzi.

19

Utracone , 293 262 249 bajtów

>:2+52*:6*:(84*+75*):>:::::[[[[[[[:[(52*)>::::[[[[[[:[84*+@>%?!<((((((((((([[[[[[[[[[[[[[ "
\#<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<\

Wypróbuj online!

Wyjaśnienie

Cały ten projekt był w górę i w dół. Ciągle myślałem, że to niemożliwe, a potem wpadłem na szalony pomysł, który może po prostu zadziałać.

Dlaczego Lost Quine jest tak trudny?

Jak zapewne wiesz, Lost to język programowania 2D, w którym położenie początkowe i kierunek są całkowicie losowe. To sprawia, że ​​pisanie każdego utraconego programu jest tak trudne, jak pisanie kodu zabezpieczonego przed promieniowaniem. Musisz wziąć pod uwagę każdą możliwą lokalizację i kierunek.

Biorąc to pod uwagę, istnieją pewne standardowe sposoby robienia rzeczy. Na przykład tutaj jest standardowy sposób drukowania łańcucha.

>%?"Stringv"(@
^<<<<<<<<<<<<<

Na dole znajduje się strumień kolekcji, który chwyta większość ips i ciągnie je do miejsca początkowego. Gdy dotrą do miejsca początkowego (lewy górny róg), dezynfekujemy je za pomocą pętli, usuwając wszystkie wartości ze stosu, a następnie obracamy bezpieczeństwo popychania sznurka i wychodzenia. (bezpieczeństwo to koncepcja unikalna dla Lost, że każdy program musi trafić %przed wyjściem, co zapobiega możliwości zakończenia programu przy starcie). Teraz moim pomysłem byłoby rozszerzenie tej formy na pełnoprawny quine.

Pierwszą rzeczą, którą trzeba było zrobić, było trochę przerobić pętlę, istniejąca pętla była specyficzna dla formatu String.

>%?!<"Stringv"(@
^<<<<<<<<<<<<<<<
^<<<<<<<<<<<<<<<

Musimy dodać drugi strumień, aby uniknąć możliwości !przeskakiwania nad strumieniem i tworzenia pętli.

Teraz chcemy to połączyć ze standardowym formatem Quine. Ponieważ Lost opiera się w dużej mierze na Kleinie, w zasadzie ukradłem pożyczyłem Klien Quine dla Martina Endera .

:2+@>%?!< "
<<<<^<<<<<<
<<<<^<<<<<<

To dość wygodnie drukuje pierwszą linię quine. Teraz wszystko, co musimy zrobić, to na stałe zakodować strumienie. Łatwiej powiedzieć, niż zrobić. Wypróbowałem około czterech różnych metod, aby to zrobić. Opiszę tylko ten, który zadziałał.

Chodzi o to, aby użyć drzwi, aby uzyskać pożądaną liczbę strzał. Drzwi to specjalny rodzaj lustra, które zmienia się za każdym razem, gdy zostanie uderzone. [odzwierciedla IPS przychodzące z lewej i ]prawej strony. Gdy trafi je ip z jednej z tych stron, orientacja przełącznika. Możemy wykonać linię tych drzwi i statyczny odbłyśnik, aby wielokrotnie wykonywać operację.

>:[[[

Wykona :trzy razy. W ten sposób, jeśli przepchniemy a <do stosu przed ręką, możemy zrobić ich dużo przy mniejszej liczbie bajtów. Wykonujemy 2 z nich, po jednym dla każdej linii, a między nimi ustanawiamy nową linię, jednak druga wystarczy tylko, dopóki nie obejmie tej !, do której ją dodaliśmy, wszystko inne może pozostać puste, oszczędzając nam kilka bajtów. Ok, teraz musimy dodać pionowe strzałki do naszych strumieni. W tym miejscu pojawia się optymalizacja klucza. Zamiast przekierowywać wszystkie IP bezpośrednio do „startu” programu, zamiast tego przekierowujemy je w skrajną lewą stronę, ponieważ już wiemy, że IP zaczynające się w skrajnej lewej musidziała (a przynajmniej będzie działać w ostatecznej wersji) możemy również po prostu przekierować inne IPS. To nie tylko sprawia, że ​​jest tańszy w bajtach, ale myślę, że ta optymalizacja umożliwia quine.

Jednak wciąż istnieją pewne problemy, z których najważniejszym jest Ips, który został uruchomiony po >wypchnięciu go, ale zanim zaczniemy robić jego kopie. Taki IPS wejdzie do kopiarki i utworzy kilka kopii 0. Jest to złe, ponieważ nasz mechanizm czyszczenia stosu używa zer do określania dolnej części stosu, pozostawiając całą wiązkę zer na dole. Musimy dodać silniejszą metodę sanity stosu. Ponieważ nie ma rzeczywistego sposobu stwierdzenia, czy stos jest pusty, będziemy musieli po prostu spróbować zniszczyć jak najwięcej przedmiotów na stosie. Tutaj ponownie zastosujemy metodę drzwi opisaną wcześniej. Dodamy ((((((((((([[[[[[[[[[[[[[do końca pierwszej linii tuż po sanitizor aby pozbyć się zer.

Teraz jest jeszcze jeden problem, ponieważ przekierowaliśmy nasze strumienie na lewy górny ips, zaczynając od %i przejście w dół już wyłączyło bezpieczeństwo i zakończy się przedwcześnie. Musimy więc wyłączyć bezpieczeństwo. Robimy to poprzez dodanie a #do strumienia, w ten sposób ips przepływający przez strumień zostanie wyłączony, ale ips, które już zostały zdezynfekowane, nie. #Musi być zakodowana w pierwszej linii, jak również.

To wszystko, mam nadzieję, że rozumiesz, jak to teraz działa.


: / tyle literówek i brakujących linków
tylko ASCII

17

Tak , 1165 879 606 561 540 522 498 + 7 = 505 bajtów

Wymaga -cheatflagi, aby umożliwić definicję aliasów.

022222120211111102222122021121202222212021112202222110222212202112110222221202122212022222102222212021222120222221022222102222210222221202222110222211022222210222221022222210222212202222221022221102211110222221022221220222212202112120221111022212202211210222212022222102211120222122022111202222120212212021221202222221022111102221210222122022222102222120212212022221102211110222122022221102222120212212022112120221111022212202112120222212=%;0e-=<;0<-=>;:0~--=1;1>=2;0%{{>0<~{~>~<<}>>>]}>]}${<#}%{@}

Wypróbuj online!

Wyjaśnienie

Są to dwie części (jak w większości quines). Dane:

022222120211111102222122021121202222212021112202222110222212202112110222221202122212022222102222212021222120222221022222102222210222221202222110222211022222210222221022222210222212202222221022221102211110222221022221220222212202112120221111022212202211210222212022222102211120222122022111202222120212212021221202222221022111102221210222122022222102222120212212022221102211110222122022221102222120212212022112120221111022212202112120222212

I dekoder:

=%;0e-=<;0<-=>;:0~--=1;1>=2;0%{{>0<~{~>~<<}>>>]}>]}${<#}%{@}

Dane są jedynie kodowaniem binarnym dekodera (a raczej jego odwrotnością). Każdy 0zaczyna nową postać, a 1s i 2s są 0- i 1bits, odpowiednio.

Zauważ, że 0jest to standardowe polecenie Yup, które przesuwa zero, podczas gdy 1i 2nie jest w tym momencie zdefiniowane. Przypisujemy jednak całą część danych do polecenia, %aby 1i 2mogły pozostać niezdefiniowane, dopóki nie %zostaną faktycznie użyte.

Następnie definiujemy kilka kolejnych poleceń:

0e-=<;
0<-=>;
:0~--=1;
1>=2;

<zmniejsza górną część stosu, >zwiększa ją. 1(nieco nieumyślnie) podwaja górę stosu. 2podwaja go, a następnie zwiększa. Dzięki tym definicjom coś takiego 0221111pozostawi na stosie 48 (110000 binarnie).

Pozostałe 32 bajty faktycznie dekodują w dwóch częściach. Najpierw musimy zrekonstruować ciąg danych.

0%                ` Push a zero and then the data.
{                 ` For each value...
  {               `   Until that value is zero...
    >0<~{~>~<<}>  `   divmod 2. The div is the input to the next iteration,
                  `   the mod gives us the next bit.
    >>]           `   Increment twice (gives 2 or 3) and put at the bottom
                  `   of the stack.
  }
  >]              ` Increment the 0 and put it at the bottom as well.
}
$                 ` Reverse the entire stack.
{<#}              ` Decrement and print each number.

I na koniec ponownie wypychamy dane i wypisujemy każdą wartość jako znak:

%{@}

Do wykorzystania w przyszłości, oto skrypt CJam do kodowania danych.


17

Fueue , 423 bajty

Fueue to esolang oparty na kolejce, w którym działającym programem jest kolejka.

)$$4255%%1(~):[)$$24%%0:<[~:)~)]~[$11~)~<[[+$4--498+*-:~-10)):])<~][)))~]<]](H-):~:[)[):~[)~:~~([:~)*[):~[$1(+48]):~+]-:~~)10)~~]/]+:5):]~:](106328966328112328136317639696111819119696281563139628116326221310190661962811611211962861109696289611619628116111612896281115421063633063961111116163963011632811111819159628151213262722151522061361613096119619190661966311961128966130281807072220060611612811961019070723232022060611

Wypróbuj online!

Jak to działa

To wyjaśnienie mogło wymknąć się spod kontroli. Z drugiej strony nie wiem, jak wyjaśnić to znacznie krócej, w sposób, w jaki mam nadzieję, że ludzie będą w stanie to zrobić.

Ściągawka Fueue

Zobacz artykuł wiki esolang, aby uzyskać szczegółowe informacje, w tym kilka funkcji nieużywanych w tym programie.

  • Program początkowy to stan początkowy kolejki, który może zawierać następujące elementy:

    • Literały całkowite (tylko w źródle tylko nieujemne, ale ujemne można obliczyć), wykonanie ich powoduje wydrukowanie znaku.
    • Bloki zagnieżdżone rozdzielone nawiasami kwadratowymi, obojętne (zachowane nienaruszone, chyba że zadziała na nie jakaś funkcja).
    • Funkcje, ich argumenty to następujące po nich elementy w kolejce:
      • +*/-%: arytmetyka liczb całkowitych ( -jest jednostkowa,% logiczna negacja). Obojętne, jeśli nie podano argumentów liczbowych.
      • ()<: wstaw element w nawiasach, usuń nawiasy z bloku, dodaj ostatni element do bloku. Dwa ostatnie są obojętne, chyba że następuje po nich blok.
      • ~:: zamiana, duplikat.
      • $: kopia (pobiera liczbę + element). Obojętny przed nieliczbowym
      • H: zatrzymanie programu.

    Zauważ, że podczas []zagnieżdżania, ()nie - te ostatnie są po prostu osobnymi funkcjami.

Składnia śledzenia wykonania

Białe znaki są opcjonalne w Fueue, z wyjątkiem cyfr. W poniższych śladach wykonania zostanie on użyty do zasugerowania struktury programu, w szczególności:

  • Kiedy funkcja się uruchomi, ona i jej argumenty zostaną wyłączone z otaczających elementów spacjami. Jeśli niektóre argumenty są skomplikowane, może być między nimi spacja.
  • Wiele śladów wykonania jest podzielonych na „blok opóźniający” po lewej stronie, oddzielony od części po prawej, która wykonuje znaczną manipulację danymi. Zobacz następną sekcję.

Nawiasy klamrowe {}(nieużywane w Fueue) są używane w śladach do reprezentowania wyniku liczb całkowitych wyrażeń matematycznych. Obejmuje to liczby ujemne, ponieważ Fueue ma tylko nieujemne literały - -jest funkcją negacji.

Różne nazwy meta-zmiennych i ...służą do oznaczania wartości i skrótów.

Opóźnianie taktyki

Intuicyjnie wykonywanie odbywa się cyklicznie wokół kolejki, częściowo modyfikując to, przez co przechodzi. Wyniki funkcji nie mogą być ponownie wykorzystane do następnego cyklu. Różne części programu ewoluują równolegle, o ile nie wchodzą w interakcje.

W rezultacie znaczna część kodu jest poświęcona synchronizacji, w szczególności opóźnieniu wykonania części programu do właściwego czasu. Istnieje wiele opcji gry w golfa, która ma tendencję do przekształcania tych części w nieczytelne obiekty BLOB, które można zrozumieć, śledząc ich wykonanie cykl po cyklu.

Te taktyki nie zawsze będą indywidualnie wymienione poniżej:

  • )[A]opóźnienia Adla cyklu. (Prawdopodobnie najłatwiejsza i najbardziej czytelna metoda).
  • ~efzamienia elementy ei fktóry opóźnia również ich wykonanie. (Prawdopodobnie najmniej czytelny, ale często najkrótszy w przypadku drobnych opóźnień).
  • $1eopóźnia pojedynczy element e.
  • -i %są przydatne do opóźniania numerów (te ostatnie dla 0i 1.)
  • Opóźniając kilka równych elementów pod rząd, :lub $można je wykorzystać do utworzenia ich z jednego.
  • (nowija się nw nawiasy, które można później wygodnie usunąć. Jest to szczególnie istotne w przypadku obliczeń numerycznych, ponieważ liczby są zbyt niestabilne, aby można je nawet skopiować bez uprzedniego umieszczenia ich w bloku.

Ogólna struktura

Pozostałe objaśnienia są podzielone na siedem części, z których każda dotyczy części działającego programu. Większe cykle, po których większość się powtarza, będą nazywane „iteracjami”, aby odróżnić je od „cykli” pojedynczych przejść przez całą kolejkę.

Oto jak dzieli się między nimi program początkowy:

A:  )$$4255%%1(~
B:  ):[)$$24%%0:<[~:)~)]~[$11~)~<[[+$4--498+*-:~-10)):])<~][)))~]<]]
C:  
D:  (H-
E:  
F:  
G:  ):~:[)[):~[)~:~~([:~)*[):~[$1(+48]):~+]-:~~)10)~~]/]+:5):]~:](106328966328112328136317639696111819119696281563139628116326221310190661962811611211962861109696289611619628116111612896281115421063633063961111116163963011632811111819159628151213262722151522061361613096119619190661966311961128966130281807072220060611612811961019070723232022060611

Duża cyfra na końcu programu koduje resztę w odwrotnej kolejności, dwie cyfry na znak, z 30 odejmowanymi od każdej wartości ASCII (np. 10Koduje a (.)

Na wyższym poziomie możesz myśleć o danych w tym programie (zaczynając od bignum) jako przepływających od prawej do lewej, ale kontrolujących przepływających od lewej do prawej. Jednak na niższym poziomie Fueue cały czas zamazuje rozróżnienie między kodem a danymi.

  • Sekcja G dekoduje bignum na cyfry ASCII (np. Cyfra 0jako liczba całkowita 48), najpierw dzieląc najmniej znaczące cyfry. Wytwarza jedną cyfrę co 15 cykli.
  • Sekcja F zawiera wygenerowane cyfry wartości ASCII (każda wewnątrz bloku), dopóki sekcja E nie będzie mogła ich wykorzystać.
  • Sekcja E obsługuje wytworzone cyfry po dwie na raz, łącząc je w bloki formularza [x[y]], a także drukując zakodowany znak każdej pary.
  • Sekcja D składa się z głęboko zagnieżdżonego bloku zbudowanego stopniowo z [x[y]]bloków w taki sposób, że gdy zawiera wszystkie cyfry, można go uruchomić, aby wydrukować wszystkie z nich, a następnie zatrzymać cały program.
  • Sekcja C obsługuje budowę sekcji D, a także odtwarza sekcję E.
  • Sekcja B odtwarza sekcję C oraz samą siebie co 30 cykli.
  • Sekcja A odlicza cykle do ostatniej iteracji pozostałych sekcji. Następnie przerywa sekcję B i uruchamia sekcję D.

Sekcja A

Sekcja A zajmuje się planowaniem końca programu. Zmniejszenie do pojedynczej funkcji wymiany zajmuje 4258 cykli ~, a następnie dostosowuje odcinek B, który zatrzymuje jego główną pętlę i zamiast tego uruchamia odcinek D.

)$ $4255% %1 (~
)$%%%...%% %0 [~]
)$%%%...% %1 [~]
⋮
)$ %0 [~]
) $1[~]
)[~]
~
  • $Funkcja tworzy 4255 kopie następujących %natomiast (owija ~w nawiasach.
  • Każdy cykl %służy do przełączania następującej liczby między 0i 1.
  • Gdy wszystkie %s zostaną zużyte, $1tworzona jest 1 kopia [~](efektywnie NOP), aw następnym cyklu )usuwa nawiasy.

Sekcja B

Sekcja B zajmuje się regeneracją, a także nową iteracją sekcji C co 30 cykli.

) : [)$$24%%0:<[~:)~)]~[$11~)~<[[+$4--498+*-:~-10)):])<~][)))~]<]]
) [)$$24%%0:<[~:)~)]~[$11~)~<[[+$4--498+*-:~-10)):])<~][)))~]<]]            [BkB]
)$ $24%     %0  :<  [~:)~)]    ~ [$11~)~<[[+$4--498+*-:~-10)):])<~][)))~]<] [BkB]
)$ %...%%% %1   < < [~:)~)] [BkB]   [$11~)~<[[+$4--498+*-:~-10)):])<~][)))~]<]
)$ %...%% %0      < [~:)~)[BkB]] [$11~)~<[[+$4--498+*-:~-10)):])<~][)))~]<]
)$ %...% %1         [~:)~)[BkB][$11~)~<[[+$4--498+*-:~-10)):])<~][)))~]<]]
⋮
) $1 [~:)~)[BkB][$11~)~<[[+$4--498+*-:~-10)):])<~][)))~]<]]
) [~:)~)[BkB][$11~)~<[[+$4--498+*-:~-10)):])<~][)))~]<]]                    (1)
~:) ~)[BkB]                 [$11~)~<[[+$4--498+*-:~-10)):])<~][)))~]<]
) : [BkB]                 ) [$11~)~<[[+$4--498+*-:~-10)):])<~][)))~]<]      (2)
) [BkB] [BkB]               $11~)~<[[+$4--498+*-:~-10)):])<~][)))~]<
  • A :duplikuje następujący duży blok (jedna kopia w skrócie [BkB]), a następnie )usuwa nawiasy kwadratowe z pierwszej kopii.
  • $$24%%0 ustawia odliczanie podobne do tego w sekcji A.
  • Podczas gdy to się odlicza, :<zamienia się <<i ~zamienia dwa bloki, umieszczając kod nowej sekcji C. na końcu.
  • Dwie <funkcje pakują dwa ostatnie bloki do pierwszego - jest to zbędne w normalnych iteracjach, ale pozwoli na ~wykonanie zadania z sekcji A na końcu.
  • (1) Po zakończeniu odliczania )usuwa zewnętrzne nawiasy. Następnie ~:)zamienia się w ):i ~)zamienia a )na początek kodu sekcji C.
  • (2) Sekcja B powraca teraz do początkowego cyklu, podczas gdy a )właśnie usuwa nawiasy klamrowe, aby rozpocząć nową iterację sekcji C.

W końcowej iteracji ~sekcja A pojawia się w punkcie (1) powyżej:

~ ) [~:)~)[BkB][$11~)~<[[+$4--498+*-:~-10)):])<~][)))~]<]]                  (1)
[~:)~)[BkB][$11~)~<[[+$4--498+*-:~-10)):])<~][)))~]<]]              )

W ~zamienia )na bloku i do sekcji C, zapobiegając sekcja B przed uruchomić ponownie.

Sekcja C

Sekcja C obsługuje scalanie nowych par cyfr w bloku sekcji D, a także tworzenie nowych iteracji sekcji E.

Poniżej pokazano typową iterację xi yreprezentację kodów ASCII cyfr. W pierwszej iteracji przychodzące elementy „D” i „E” są początkowe [H]i -zamiast tego, ponieważ żadna poprzednia sekcja E nie uruchomiła się, aby utworzyć pary cyfr.

C                                               D             E
$11~ )  ~<[[+$4--498+*-:~-10)):])<~]  [)))~]  < [)))~[...]]   [x[y]]
~~~ ~~~ ~~~ ~~) [[+$4--498+*-:~-10)):])<~]  < [)))~] [)))~[...][x[y]]]
~~~ ~~~     )  ~ [[+$4--498+*-:~-10)):])<~] [)))~[)))~[...][x[y]]]]
~~~       ~ )   [)))~[....]]                                  [[+$4--498+*-:~-10)):])<~]
                                              ~~[)))~[....]] )[[+$4--498+*-:~-10)):])<~]
                                                [)))~[....]]  ~[+$4--498+*-:~-10)):])<~
  • Używa innej metody synchronizacji, którą odkryłem dla tej odpowiedzi. Gdy masz kilka funkcji zamiany ~w jednym rzędzie, rząd zmniejsza się do około 2/3 każdego cyklu (ponieważ jeden ~zamienia dwa kolejne), ale czasami z resztą ~s, która siejąc spustoszenie, ostrożnie manipuluje następującymi.
  • $11~produkuje taki rząd. Następny ~zamienia a <w następnym bloku. Inny <na końcu dołącza nowy blok par cyfr (cyfry xiy jako kody ASCII) do bloku sekcji D.
  • W następnym cyklu ~wiersz ma ~~resztę, która zamienia a ~na następną ). Druga <dołącza sekcję D do [)))~]bloku.
  • Następnie ~sama zamiana zamienia następujący blok z nowym kodem sekcji E w bloku sekcji D. Następnie nowa resztka ~zamienia krzyż ), a na koniec ostatni ~~z ~rzędu zamienia jeden z nich na odcinek E, gdy tylko )usunął nawiasy.

W końcowej iteracji sekcja A ~zamieniła )przekrój przez sekcję B i na sekcję C. Jednak sekcja C jest tak krótkotrwała, że ​​już zniknęła, a )kończy się na początku sekcji D.

Sekcja D

Sekcja D zajmuje się wydrukowaniem ostatniej dużej cyfry i zatrzymaniem programu. Przez większość przebiegu programu jest to obojętny blok, w którym sekcje B – G współpracują przy budowie.

    (H -
    [H]-
    ⋮
    [)))~[H-]]                  After one iteration of section C
    ⋮
    [)))~[)))~[H-][49[49]]]]    Second iteration, after E has also run
    ⋮
)   [)))~[...]]     [49[48]]    Final printing starts as ) is swapped in
    ))) ~[...][49[48]]
    )) )[49[48]] [...]
    )) 49 [48][...]             Print first 1
    ) )[48] [...]
    ) 48 [...]                  Print 0
    )[...]                      Recurse to inner block
    ...
    ⋮
    )[H-]                       Innermost block reached
    H -                         Program halts
  • W pierwszym cyklu programu (funkcja nawijania otacza Hnawiasy. -Poniżej, będzie stosowany jako obojętne element pierwszej iteracji zamiast cyfr pary.
  • Włączona jest pierwsza para cyfr rzeczywistych [49[49]], odpowiadająca końcowej 11cyfrze.
  • Bardzo ostatnia cyfra pary [49[48]](odpowiadający 10na początku liczebnika) w rzeczywistości nie jest włączona do bloku, ale to nie ma znaczenia, jak )[A[B]]i )[A][B]odpowiadają zarówno zmienia się A[B].

Po ostatniej iteracji następuje )zamiana w prawo z sekcji B i blok sekcji D zostaje odblokowany. Na )))~początku każdego podbloku upewnia się, że wszystkie części są wykonywane we właściwej kolejności. Wreszcie najbardziej wewnętrzny blok zawiera Hzatrzymanie programu.

Sekcja E

Sekcja E obsługuje łączenie par cyfr ASCII wytworzonych przez sekcję G i obie drukują odpowiedni zakodowany znak i wysyła blok z połączoną parą w lewo do sekcji C i D.

Ponownie poniżej pokazano typową iterację xi yreprezentację kodów ASCII cyfr.

E                                                   F
~ [+$4--498+*-:~-10)):] )              <  ~         [y] [x]
) [+$4--498+*-:~-10)):]                   < [x] [y]
+ $4-  - 498  +*- :~ -10 ) )              : [x[y]]
+---  -{-498} +*- ~~{-10} )       ) [x[y]]  [x[y]]
+--    - 498  +*   -{-10}       ~ ) x  [y]  [x[y]]
+-    -{-498} +               * 10 x  )[y]  [x[y]]
+      - 498                    + {10*x} y  [x[y]]
                         + {-498} {10*x+y}  [x[y]]
{10*x+y-498}  [x[y]]
[x[y]]
  • Przychodzące bloki cyfr są zamieniane, następnie blok y jest dołączany do bloku x, a cały blok pary jest kopiowany. Jedna kopia pozostanie do końca dla sekcji C i D.
  • Druga kopia jest ponownie odblokowana, a następnie do obliczenia stosowana jest sekwencja funkcji arytmetycznych 10*x+y-498, wartość ASCII zakodowanego znaku. 498 = 10*48+48-30, 48s cofnie kodowanie ASCII xi ypodczas gdy 30przesuwa kodowanie z 00–99na 30–129, co obejmuje wszystkie drukowalne ASCII.
  • Wynikowy numer jest następnie pozostawiony do wykonania, co wypisuje jego znak.

Sekcja F.

Sekcja F składa się z obojętnych bloków zawierających kody cyfr ASCII. W przypadku większości uruchomionych programów będą tu maksymalnie dwa, ponieważ sekcja E zużywa je z tą samą prędkością, z jaką wytwarza je G. Jednak w końcowej fazie drukowania 0zostaną tutaj zebrane zbędne cyfry.

[y] [x] ...

Sekcja G

Sekcja G obsługuje dzielenie dużej liczby na końcu programu, najpierw najmniej znaczących cyfr, i wysyłanie bloków z kodami ASCII w lewo do innych sekcji.

Ponieważ nie ma kontroli zatrzymania, w rzeczywistości będzie kontynuował generowanie 0cyfr, gdy liczba zmniejszy się do 0, dopóki sekcja D nie zatrzyma całego programu z Hfunkcją.

[BkG] skraca kopię dużego bloku kodu początkowego, który służy do samoreplikacji w celu rozpoczęcia nowych iteracji.

Inicjalizacja w pierwszych cyklach:

) :~  : [)[):~[)~:~~([:~)*[):~[$1(+48]):~+]-:~~)10)~~]/]+:5):]~:]  ( 106328966328112328136317639696111819119696281563139628116326221310190661962811611211962861109696289611619628116111612896281115421063633063961111116163963011632811111819159628151213262722151522061361613096119619190661966311961128966130281807072220060611612811961019070723232022060611
)  ~ ~ [)[):~[)~:~~([:~)*[):~[$1(+48]):~+]-:~~)10)~~]/]+:5):]~:]  [BkG] [10...11]
) [)[):~[)~:~~([:~)*[):~[$1(+48]):~+]-:~~)10)~~]/]+:5):]~:]     ~ [BkG] [10...11]
) [):~[)~:~~([:~)*[):~[$1(+48]):~+]-:~~)10)~~]/]+:5):]       ~ : [10...11]  [BkG]

Typowa iteracja Noznacza liczbę do podzielenia:

) [):~[)~:~~([:~)*[):~[$1(+48]):~+]-:~~)10)~~]/]+:5):]        ~ : [N]  [BkG]
) :~ [)~:~~([:~)*[):~[$1(+48]):~+]-:~~)10)~~]/]+ :5 )         : [N]  : [BkG]
)  ~ ~ [)~:~~([:~)*[):~[$1(+48]):~+]-:~~)10)~~]/]  +5 5     ) [N]  [N] [BkG] [BkG]
) [)~:~~([:~)*[):~[$1(+48]):~+]-:~~)10)~~]/]               ~ 10 N  [N] [BkG] [BkG]
) ~:~  ~ ( [:~)*[):~[$1(+48]):~+]-:~~)10)~~]               / N 10  [N] [BkG] [BkG]
)  ~ : [:~)*[):~[$1(+48]):~+]-:~~)10)~~]                 ( {N/10}  [N] [BkG] [BkG]
) [:~)*[):~[$1(+48]):~+]-:~~)10)~~]                    : [{N/10}]  [N] [BkG] [BkG]
:~ )*[):~[$1(+48]):~+]- :~ ~)10 )           ~ ~ [{N/10}]  [{N/10}] [N] [BkG] [BkG]
~~) *[):~[$1(+48]):~+]- ~~10 )             ) [{N/10}]  ~ [{N/10}] [N]  [BkG] [BkG]
)  ~ * [):~[$1(+48]):~+]  -10            ~ ) {N/10}  [N] [{N/10}] [BkG] [BkG]
) [):~[$1(+48]):~+]               * {-10} {N/10}  ) [N]  [{N/10}] [BkG] [BkG]
) :~ [$1(+48]) :~                 + {-10*(N/10)} N  [{N/10}] [BkG] [BkG]
)  ~ ~ [$1(+48]  )                 ~ ~ {N%10}  [{N/10}] [BkG] [BkG]
) [$1(+48]                 ~ ) {N%10}  ~ [{N/10}] [BkG]  [BkG]
$1(                     + 48 {N%10}    ) [BkG]  [{N/10}] [BkG]
                        ( {48+N%10}   BkG [{N/10}] [BkG]            New iteration starts
                        [{48+N%10}]   ....
  • Kropla opóźniająca jest tutaj szczególnie owłosiona. Jednak jedyną nową sztuczką opóźniającą jest użycie +:5zamiast --10opóźnienia 10dwóch cykli. Niestety 10pomógł tylko jeden z programów.
  • [N]I [BkG]bloki są powielane, a następnie jeden egzemplarz Njest podzielona 10.
  • [{N/10}]jest duplikowane, wówczas do obliczenia kodu ASCII ostatniej cyfry Nas stosuje się więcej funkcji arytmetycznych 48+((-10)*(N/10)+N). Blok z tym kodem ASCII pozostawia się w sekcji F.
  • Druga kopia [{N/10}]zostaje zamieniona między [BkG]blokami, aby ustawić początek nowej iteracji.

Quine bonusowa (540 bajtów)

)$$3371%%1[~!~~!)!]):[)$$20%%0[):]~)~~[)$$12%%0[<$$7%~~0):~[+----48+*-~~10))]<]<~!:~)~~[40~[:~))~:~[)~(~~/[+--48):]~10]+30])):]]][)[H]](11(06(06(21(21(25(19(07(07(19(61(96(03(96(96(03(11(03(63(11(28(61(11(06(06(20(18(07(07(18(61(11(28(63(96(11(96(96(61(11(06(06(19(20(07(07(18(61(30(06(06(25(07(96(96(18(11(28(96(61(13(15(15(15(15(22(26(13(12(15(96(96(19(18(11(11(63(30(63(30(96(03(28(96(11(96(96(61(22(18(96(61(28(96(11(11(96(28(96(61(11(96(10(96(96(17(61(13(15(15(22(26(11(28(63(96(19(18(63(13(21(18(63(11(11(28(63(63(63(61(11(61(42(63(63

Wypróbuj online!

Ponieważ nie byłem pewien, która metoda będzie najkrótsza, najpierw spróbowałem zakodować znaki jako liczby dwucyfrowe oddzielone (s. Kod podstawowy jest nieco krótszy, ale rekompensuje to 50% większa reprezentacja danych. Nie tak golfowy jak ten drugi, ponieważ zatrzymałem się, kiedy zdałem sobie sprawę, że to nie przebije. Ma jedną zaletę: nie wymaga implementacji z obsługą bignum.

Jego ogólna struktura jest nieco podobna do głównej. Brak sekcji G, ponieważ reprezentacja danych wypełnia bezpośrednio sekcję F. Jednak sekcja E musi wykonać podobne obliczenia divmod, aby zrekonstruować cyfry liczb dwucyfrowych.


1
Powinieneś
zagrać w

1
)$n[)](jest bajtem krótszym dla licznika opóźnienia.
jimmy23013

15

Galaretka, 3 bajty

”ṘṘ

Wypróbuj online!

Weryfikacja

$ echo $LANG
en_US
$ xxd -g 1 quine.jelly
0000000: ff cc cc                                         ...
$ ./jelly f quine.jelly | xxd -g 1
0000000: ff cc cc                                         ...

Jak to działa

”ṘṘ    Main link. No input.

”Ṙ     Set the return value to the character 'Ṙ'.
  Ṙ    Print a string representation of the return value.
       This prints: ”Ṙ
       (implicit) Print the return value.
       This prints: Ṙ

Z jakiej wersji interpretera korzysta ta funkcja? Kiedy go testuję, wysyła sygnał wyjściowy w UTF-8, nawet jeśli dane wejściowe znajdują się na stronie kodowej Jelly (a zmiana kodowania sprawiłaby, że nie jest to quine).

1
Kodowanie wyjścia zależy od ustawień twojego terminala: jeśli jest ustawiony na UTF-x, używa tego; jeśli jest ustawiony na cokolwiek innego, używa strony kodowej Jelly. W systemie Linux LANG=en_USosiąga właśnie to. tio.run/nexus/bash#@@/…
Dennis,
Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.