Befunge, 344 bayt
&v>>>#p_:63p:43g`\!+v>/*53g+\01g:2%2*1-\2/!*63g+\0\:v
40$ v++!\`g14:p35:\<^2\-1*2%2p10::%4+g00:\g36\g35-1_v
#11^$_83p73v >1+:41g`!#v_$,1+:43g`!#v_@>->2>+00p+141^_
<p1^ vp< ^,g+7g36:<<<<1+55p36:<<<< ^1?0^#7g36g35*
8&p|!++!%9#2g+7g10\*!-g38g10!-g37:g00!!*<>3^
443>:!#v_>>1-::3%1-:53g+00p\3/1-:63g+01p^
^>^>>$#<"#"53g63g7+p41g53g-43g63g-+!#^_
Çevrimiçi deneyin!
MATLAB yanıtlarında @flawr'ın belirttiği gibi, alan boyutu önemsiz olmayan bir boyuttaysa bu biraz zaman alabilir. Aslında, bitmesini beklemeye gerçekten değmeyecek bir duruma girmek oldukça kolaydır, çünkü zamanın sonuna kadar beklemeniz muhtemeldir.
Bunun neden olduğunu anlamak için, programı Befunge'nin birçok "görsel hata ayıklayıcısından" birinde yürütürken görüntülemek yararlıdır. Befunge'de veri ve kod aynı şey olduğundan, yolu zaman içinde değiştikçe görüntüleyebilirsiniz. Örneğin, yavaş bir yolda koşunun bir kısmının nasıl görünebileceğini gösteren kısa bir animasyon.
Algoritma, alan sınırının altındaki sola doğru bu kader dönüşünü yapmaya karar verdiğinde, esasen kendisini ömür boyu amaçsız bir gezintiye mahkemm etti. Bu noktadan sonra, çitle çevrili alanda geri dönüp sağa dönmeyi denemeden önce mümkün olan her yolu takip etmelidir. Ve bu durumlarda potansiyel yolların sayısı kolayca astronomik hale gelebilir.
Alt satır: Uzun zaman alıyor gibi görünüyorsa, muhtemelen yürütmeyi iptal etmek ve tekrar başlamak iyi bir fikirdir.
açıklama
Bu temelde, alandaki olası her yolu deneyen ve daha sonra sıkıştığında izlenen çözme adımlarını tekrarlayan bir algoritmadır. Befunge işlev kavramına sahip olmadığından, yinelemeli bir işlev söz konusu değildir, ancak yığındaki durumu izleyerek süreci taklit edebiliriz.
Bu, yığını takip etmek isteyebileceğimiz potansiyel koordinatlarla doldurarak çalışır. Sonra bir kümeyi yığından çekeriz ve uygun olup olmadığını kontrol ederiz (yani aralıkta ve mevcut bir yolla çakışmıyor). İyi bir noktaya #
ulaştığımızda, o konumdaki oyun alanına a yazarız ve daha sonra geri gitmemiz gerektiğinde bu ayrıntıları yığına ekleriz.
Daha sonra, bu yeni konumdan alabileceğimiz potansiyel yolları belirten yığına (rastgele sırayla) ek dört koordinat kümesi ekliyoruz ve döngünün başına atlıyoruz. Potansiyel yollardan hiçbiri uygun değilse, #
yazdığımız yerin konumunu kaydettiğimiz yığındaki noktaya ulaşacağız , bu nedenle bu adımı geri alacağız ve bir adım öncesinden potansiyel koordinatları denemeye devam edeceğiz.
Vurgulanan çeşitli bileşen parçaları ile kod şöyle görünür:
Alanın genişliğini ve yüksekliğini okuyun ve 0
geri izleme konumundan ziyade potansiyel bir yolu belirtmek için başlangıç koordinatlarını bir tür işaretleyicisiyle birlikte itin . Basit bir komutla geri döndürülen geri
izleme konumlarını ( 1
tür işaretçisi ile gösterilir) kontrol edin p
, çünkü bunlar oyun alanına bir boşluk yazmak için gereken tam formatta saklanır.
Koordinatların hala oyun alanının içinde olup olmadığını kontrol edin. Menzil dışındaysa, bir sonraki potansiyel koordinatları denemek için bunları yığından çıkarın ve geri döngü yapın.
Menzil içinde iseler, bir sonraki adımın yeri olan yığından sonraki iki değeri alın (bunu izleyen testte gereklidir).
Koordinatların yolun mevcut bir segmentiyle temas edip etmeyeceğini kontrol edin. Bir önceki adımın yeri bu kontrolden açıkça göz ardı edilmiştir.
Tüm testler başarılı olursa, #
oyun alanına a yazın ve hedef konuma ulaşıp ulaşmadığımızı kontrol edin.
Varsa, son yolu yazın ve çıkın.
Aksi takdirde, koordinatları 1
daha sonra geriye doğru izlemek için bir tür işaretleyiciyle yığına kaydedin .
Bu, yakında ihtiyaç duyacağımız rastgele bir sayı hesaplaması ile kesilir.
Geçerli konumdan ulaşılabilecek dört potansiyel hedefi itin. Rastgele sayı, itildikleri sırayı ve dolayısıyla izlenecekleri sırayı belirler.
Ana döngünün başlangıcına geri sarın ve yığındaki sonraki değerleri işleyin.