:?
:
#/)
\ #
!"*@
"
Çevrimiçi deneyin!
Bu, sonuçları C, B, A
satır beslemeleri ile ayrılmış sırayla verir .
açıklama
Her zamanki gibi, kısa bir Labyrinth primer:
- Labirentte, başlangıçta (örtük) sonsuz miktarda sıfır ile dolu , ana ve aux (iliary) olmak üzere iki rasgele hassas tam sayı yığını vardır . Biz sadece kullanarak olacak ana Bu yanıt için.
- Kaynak kod, bir labirenti andırır, burada talimat göstergesinin (IP) olabildiğince koridorları takip ettiği (hatta köşelerinde). Kod, okuma sırasındaki ilk geçerli karakterde başlar, yani bu durumda sol üst köşede. IP herhangi bir birleşme şekline geldiğinde (yani, geldiğine ek olarak birkaç bitişik hücre), ana yığının tepesine dayalı bir yön seçecektir. Temel kurallar şunlardır: negatifken sola dönün, sıfırda ilerlemeye devam edin, pozitifken sağa dönün. Ve bunlardan biri mümkün olmadığında, çünkü bir duvar var, o zaman IP ters yön alır. IP ayrıca ölü uçlara çarptığında da döner.
"
Düzeni biraz israflı yapan iki no-op'a ( ) rağmen, bu çözümden oldukça memnunum, çünkü kontrol akışı aslında oldukça ince.
IP, :
sağdaki sol üst köşede başlar . Derhal bir çıkmaza girecek ?
ve geri dönecek, böylece program aslında bu doğrusal kod parçasıyla başlayacak:
: Duplicate top of main stack. This will duplicate one of the implicit zeros
at the bottom. While this may seem like a no-op it actually increases
the stack depth to 1, because the duplicated zero is *explicit*.
? Read n and push it onto main.
: Duplicate.
: Duplicate.
Bu, şimdi n
ana yığında üç kopyaya sahip olduğumuz anlamına geliyor , ancak derinliği 4
. Bu uygundur, çünkü girişin kopyaları boyunca çalışırken mevcut çarpanı almak için yığın derinliğini alabileceğimiz anlamına gelir.
IP şimdi (saat yönünde) 3x3 döngüsüne giriyor. Not #
yığın derinliğini iter ki, her zaman IP hep bu noktada doğu dönecek biliyorum öyle ki pozitif bir değer itecektir.
Döngü gövdesi şudur:
# Push the stack depth, i.e. the current multiplier k.
/ Compute n / k (rounding down).
) Increment.
# Push the stack depth again (this is still k).
* Multiply. So we've now computed (n/k+1)*k, which is the number
we're looking for. Note that this number is always positive so
we're guaranteed that the IP turns west to continue the loop.
" No-op.
! Print result. If we've still got copies of n left, the top of the
stack is positive, so the IP turns north and does another round.
Otherwise, see below...
\ Print a linefeed.
Then we enter the next loop iteration.
Döngü !
üç defa (en fazla ) travers edildikten sonra , tüm kopyaları n
tükenir ve altındaki sıfır açığa çıkar. Nedeniyle "
(Aksi oldukça yararsız görünüyor) altındaki bu pozisyon bir kavşak olduğunu. Bu, yığının üstündeki sıfır ile, IP dümdüz ilerlemeye çalışır (batı), ancak bir duvar olduğu için aslında 180 derecelik bir dönüş yapar ve bir çıkmaza çarpmış gibi doğuya geri döner.
Sonuç olarak, aşağıdaki bit şimdi yürütülür:
" No-op.
* Multiply two zeros on top of the stack, i.e. also a no-op.
The top of the stack is now still zero, so the IP keeps moving east.
@ Terminate the program.
C B A
açıkça belirtilmişse (tutarlı bir şekilde) sonuçları farklı bir sırayla (örneğin ) verebilir miyiz?