Wprowadzenie
Kipple to ezoteryczny język programowania oparty na stosach, opracowany przez Rune Berg w marcu 2003 roku.
Kipple ma 27 stosów, 4 operatorów i strukturę kontrolną.
Półki na książki
Stosy są nazywane a
- z
i zawierają 32-bitowe liczby całkowite ze znakiem. Istnieje również specjalny stos @
, aby ułatwić wyprowadzanie liczb. Kiedy liczba jest wypychana na @
, wartości ASCII cyfr tego numeru są w rzeczywistości wypychane. (Na przykład, jeśli naciśniesz 12 do @
, popchnie 49, a następnie 50 do @
.)
Dane wejściowe są wypychane na stos wejściowy i
przed uruchomieniem programu. Interpretator poprosi o zapisanie wartości i
przed wykonaniem. Po zakończeniu wykonywania wszystko na stosie wyjściowym o
jest wyskakujące na wyjście jako znak ASCII. Ponieważ jest to jedyny mechanizm IO Kipple, interakcja z programem Kipple jest niemożliwa.
Operatorzy
Operand jest albo identyfikatorem stosu, albo 32-bitową liczbą całkowitą ze znakiem.
Naciśnij: >
lub<
Składnia: Operand>StackIndentifier
lubStackIndentifier<Operand
Operator Push przenosi operand w lewo i wypycha go na określony stos. Na przykład 12>a
wypchnie wartość 12 na stos a
. a>b
wyskoczy najwyższą wartość ze stosu a
i wrzuci ją na stos b
. Stuknięcie pustego stosu zawsze zwraca 0. a<b
jest równoważne z b>a
. a<b>c
wyskakuje najwyższa wartość z b
i popycha do obu c
i a
.
Dodaj: +
Składnia: StackIndentifier+Operand
Operator Add wypycha sumę najwyższego elementu ze stosu i operandu na stos. Jeśli operand jest stosem, wartość jest z niego wyskakująca. Na przykład, jeśli najwyższą wartością stosu a
jest 1, wówczas a+2
popchnie na niego 3. Jeśli a
jest pusty, wówczas a+2
popchnie 2 na niego. Jeśli najwyższe wartości stosu a
i b
wynoszą 1 i 2, wówczas a+b
wyskakuje wartość 2 ze stosu b
i wypycha 3 na stos a
.
Odejmować: -
Składnia: StackIndentifier-Operand
Operator Subtract działa dokładnie tak samo, jak operator Add, z tym wyjątkiem, że odejmuje zamiast dodawać.
Jasny: ?
Składnia: StackIndentifier?
Operator Clear opróżnia stos, jeśli jego najwyższy element to 0.
Interpreter ignoruje wszystko, co nie jest obok operatora, więc następujący program będzie działać: a+2 this will be ignored c<i
. Jednak właściwym sposobem dodawania komentarzy jest użycie #
znaku. #
Przed wykonaniem usuwane jest wszystko od znaku do końca wiersza. Znak ASCII # 10 jest zdefiniowany jako koniec linii w Kipple.
Operandy mogą być współużytkowane przez dwóch operatorów, np. a>b c>b c?
Mogą być zapisane jako a>b<c?
.
Program 1>a<2 a+a
będzie a
zawierał wartości [1 4]
(od dołu do góry), a nie [1 3]
. Podobnie dla -
operatora.
Struktura kontroli
W Kipple jest tylko jedna struktura kontrolna: pętla.
Składnia: (StackIndentifier code )
Dopóki określony stos nie jest pusty, kod w pasujących nawiasach będzie powtarzany. Pętle mogą zawierać inne pętle. Na przykład (a a>b)
przeniesie wszystkie wartości stosu a
na stos b
, chociaż kolejność zostanie odwrócona . Funkcjonalnie identyczny, ale bardziej elegancki sposób to zrobić (a>b)
.
Przykłady
100>@ (@>o)
To wyjdzie 100
33>o 100>o 108>o 114>o 111>o 87>o 32>o 111>o 108>o 108>o 101>o 72>o
To zostanie wydrukowane "Hello World!"
. Kiedy o
stos jest wyprowadzany, zaczyna wyrywać znaki od góry stosu do dołu.
#prime.k by Jannis Harder
u<200
#change 200
k<2>m
u-2
(u-1 u>t u>z u<t
(k>e e+0 e>r)
(e>k)
m+1
m>t
m>z
m<t
t<0>z? t?
1>g
(r>b
m+0 m>a
b+0 b>w
(a-1
b+0 b>j
j?
1>s
(j<0>s j?)
s?
(s<0 w+0 w>b s?)
a>t
a>z
t>a
b-1
b>t
b>z
t>b
z<0>t? z?
a?)
b?
1>p
(b<0 b? 0>p)
p?
(p 0>r? 0>p? 0>g)
)
g?
(g m+0 m>k 0>g?)
u?)
(k>@
10>o
(@>o)
)
Jest to generator liczb pierwszych, ale nie jestem pewien, jak to działa.
Zasady
Musisz napisać program / funkcję, która interpretuje Kipple. Ten program / funkcja może uzyskać program Kipple za pośrednictwem pliku źródłowego lub uzyskać go za pośrednictwem STDIN bezpośrednio od użytkownika. Jeśli STDIN nie jest dostępny, musi pobrać go z klawiatury i kontynuować wprowadzanie, dopóki nie zostanie wprowadzony określony znak niedrukowalny. Na przykład, jeśli interpreter jest napisany w kodzie maszynowym x86, pobierze znak programu Kipple po znaku z klawiatury i będzie to robił do momentu escnaciśnięcia (lub dowolnego innego klawisza, który nie emituje znaku drukowalnego).
Jeśli wystąpi błąd, np. Błąd składniowy lub przepełnienie stosu, musi w jakiś sposób potwierdzić to, na przykład zwracając 10 zamiast 0 lub komunikaty o błędach generowane przez interpreter / kompilator, ALE NIE WIADOMOŚCI O BŁĘDACH .
Do tego wyzwania obowiązują wszelkie inne regularne zasady gry w golfa kodowego.
Twój kod zostanie przetestowany z niektórymi przykładami w archiwum próbek Kipple
To jest golf golfowy . Wygra najkrótszy kod w bajtach. Powodzenia!
Zauważ, że w Kipple istnieje opcjonalny operator "
, ale nie jest on częścią specyfikacji, a jedynie dodatkową funkcją w oficjalnym tłumaczu. Nie wspomniałem o tym tutaj, więc nie musi być poparty w twoim zgłoszeniu.
Jeśli masz jakiekolwiek wątpliwości co do jakiejkolwiek części specyfikacji, możesz to sprawdzić za pomocą oficjalnego tłumacza napisanego w Javie . Spowoduje to pobranie pliku zip zawierającego skompilowany program i kod źródłowy. Jest licencjonowany na licencji GPL.
źródło
i
jeśli pobieram program źródłowy ze standardowego wejścia?Odpowiedzi:
C,
709702 bajtówWynik w bajtach został usunięty z nowej linii (którą można usunąć), ale dla ułatwienia czytania zamieszczam ją tutaj z nową linią:
Kompiluj z
gcc -w golf.c
(-w
wycisza ostrzeżenia dla twojego zdrowia psychicznego).Obsługuje wszystko oprócz
i
danych wejściowych, ponieważ pytający nie odpowiedział jeszcze na moje pytanie, jak to zrobić, jeśli weźmiesz kod ze standardowego wejścia. Nie zgłasza błędów składniowych.źródło
./a.out < prime.k
.Rubinowy, 718 bajtów (obecnie niekonkurencyjny)
jestem bardzo zmęczony
Plik jest ładowany jako argument wiersza poleceń, a dane wejściowe są przesyłane przez STDIN. Alternatywnie, potokuj plik do STDIN, jeśli nie potrzebujesz danych wejściowych do
i
rejestru.Z powodu pewnych nieporozumień dotyczących specyfikacji bieżąca wersja nie obsługuje sięa<b>c
poprawnie, a zatem nie jest konkurencyjna, dopóki nie zostanie naprawiona.a<b>c
jest teraz naprawiony. Jednak nadal zwraca zły wynik podczas uruchamiania funkcji liczb pierwszych, więc nadal pozostaje odpowiedzią niekonkurencyjną.źródło
0 1 1 2 4 8 16...
Zastanawiam się, czy to błąd specyfikacjia+0
jest nonsensowna/(\((\g<1>|\s)+\)|[^()\s]+)/m
, którego używa do dzielenia na tokeny i grupy tokenów. ( Przetestuj na regex101 ). Prawdopodobnie jest to błąd w pozostałej części parsowania, ale nie wiem gdzie.