Labirentten kaç!


20

Bu 5x5 labirentte sıkışıp kaldınız - her oda 1'den 25'e etiketlendi ve çıkış oda 1'de.

resim açıklamasını buraya girin

Şu anda bulunduğunuz odaya giriş olarak verilir. Göreviniz oda 1'e ulaşmak için gereken en kısa hamle sırasını (kuzey, doğu, güney, batı) elde etmektir.

Hareketleri, karakterleri kullandığınız sürece istediğiniz herhangi bir biçimde (liste, dize, dizi ...) çıktı alabilirsiniz n,w,e,s.

İşte tüm test örnekleri:

1 => empty string/list
2 => w
3 => ww
4 => swwnw
5 => wswwnw
6 => seenwnw
7 => nw
8 => wnw
9 => wwnw
10 => swwnwnw
11 => eenwnw
12 => enwnw
13 => nwnw
14 => wnwnw
15 => wwnwnw
16 => enenwnw
17 => nenwnw
18 => wnenwnw
19 => nwnwnw
20 => wnwnwnw
21 => nenenwnw
22 => enwnenwnw
23 => nwnenwnw
24 => wnwnenwnw
25 => nwnwnwnw

Bayt cinsinden en kısa cevap kazanır!


3
Oda etiketlemesi / girişi ne kadar esnektir? 1-endeks yerine 0-indeksleyebilir miyiz? Oda numarasını karakter olarak alabilir miyiz (temel 36'da olduğu gibi düşünme)?
Chas Brown

2
@ Therandomguy hayır, bu özel labirenti ele almanız gerekiyor.
Arnaud

6
Mümkün olduğu için, tüm olası vakaların test vakalarına dahil edilmesi gerektiğini düşünüyorum.
Jonathan Frech

1
@UnrelatedString Bu soru 1 girdi alır ve girdisine bağlı olarak farklı bir yol çıkarır. Bu gereksinimin kolmogorov-karmaşıklık etiketine uymadığına inanıyorum .
tsh

2
Birinin Labirent'te bir cevap vermesi gerekiyor .
Draco18s

Yanıtlar:


20

Python 2 , 64 bayt

def f(n):d=0x1211252b5375>>2*n-4&3;print"nwes"[d];f(n+d*3+d%2-5)

Çevrimiçi deneyin!

Her satıra bir yön yazdırarak hata ile sonlanan bir işlev.

Sabit 0x1211252b53754 tabanındaki dher bir oda numarasından 0 ila 3 arasında hareket ettiğimiz yönü kodlar. Çıkarma basamağı >>2*n-4&3, n=1kodu sonlandırırken negatif bir kaydırma hatası vermek üzere tasarlanmıştır . Biz oda numarasını güncellemek nyoluyla bir ofset bu yönde hesaplanan en dolarak d*3+d%2-5eşleştiren:

d   d*3+d%2-5
0  -> -5
1  -> -1
2  ->  1
3  ->  5 

1
Bunun olduğu gibi geçerli olduğundan emin değilim, işlevler yeniden kullanılabilir olmalı ve bu işlevi çağırdıktan sonra yürütmeye devam edebilmek için hata yakalama ( try/ except) gerekir.
Outgolfer Erik


6

05AB1E , 30 29 bayt

Asal sayılarla mucizevi bir tesadüf sayesinde -1 bayt

[Ð#•θzƶ‰`Ó•4вsè<DˆØ·5-+}'‹™¯è

Çevrimiçi deneyin!

[                      }    # infinite loop:
 Ð                          #  triplicate the room number (initially, the input)
  #                         #  break if room number == 1
   •θzƶ‰`Ó•4в               #  compressed list 202232302231102210202010
             sè             #  use the room number to index into that list
               <            #  decrement
                Dˆ          #  add a copy to the global array
                  Ø         #  nth prime (-1 => 0, 0 => 2, 1 => 3, 2 => 5)
                   ·        #  double
                    5-      #  subtract 5
                      +     #  add that to the room number
'‹™                         # dictionary string "western"
   ¯                        # push the global array
    è                       # index (wraps around, so -1 => n, 0 => w, 1 => e, 2 => s)

1
Bu11 , boş bir dize yerine giriş için çıktılar (kolay düzeltme satır aralığı eklemek olacaktır õ?). Bunun dışında güzel bir cevap!
Kevin Cruijssen

1
@KevinCruijssen bu hatayı gösterdiğin için teşekkürler! Tek baytlık bir düzeltme buldum.
Grimmy

5

Yakut , 72 62 bayt

f=->n{n<2?'':' en  sw'[x=4*18139004[n]+6*4267088[n]-5]+f[n+x]}

Çevrimiçi deneyin!

Nasıl?

Buradaki hile, her hücre için bir sonraki adımı oluşturmak için 2 sabit kullanmak ve ardından sorunu tekrar tekrar çözmek.

2 sabit 18139004 ve 4267088 bir sonraki hareketin yönünü veren ikili dizgilerdir, her hücre için her ikisinden tek bir bit çıkararak şunları elde edebiliriz:

"n" = 4*0+6*0-5 = -5
"w" = 4*1+6*0-5 = -1
"e" = 4*0+6*1-5 = +1
"s" = 4*1+6*1-5 = +5

Tek bir büyük ikili sayı IMHO'yu kaydırmaktan ve maskelemekten daha kolaydır.

Yönü aldığımızda, karşılık gelen harfi "en sw" dizesinden çıkarırız:

  1   5
  |   |
" en  sw"
   |   |
  -5  -1

Ve hücre üzerinde yinelemeli olarak ilerle [n + x]






2

Kömür , 43 40 bayt

NθW⊖θ«≔I§”)“⊞x⟧∧⎚⁵2”ιι§nwesι≧⁺⁻⁺﹪ι²×³ι⁵θ

Çevrimiçi deneyin! Bağlantı, kodun ayrıntılı versiyonudur. @ @ ChasBrown ve @ xnor'ın cevaplarına dayanarak. Açıklama:

Nθ

Odaya girin.

W⊖θ«

Döngü değişkenini ioda numarasından bir taneye ayarlayın ve sıfır olmadığında tekrarlayın.

«≔I§”)“⊞x⟧∧⎚⁵2”ιι

Sıkıştırılmış dizeden yönü çıkarın 0113130113220112010102010. (Önde gelen 0sadece bir dolgu rakamıdır.)

§nwesι

Yönü yazdırın.

≧⁺⁻⁺﹪ι²×³ι⁵θ

Yeni oda numarasını hesaplamak için @ xnor formülünü kullanın.


2

Jöle , 30 29 bayt

“þ&ƊĿñ÷°e’b6Ḥ_5Ż⁸+ị¥ƬI‘ị“®ȯẹ»

Çevrimiçi deneyin!

Başlangıç ​​hücresini alan ve yönlerle birlikte bir dize döndüren monadik bir bağlantı.

Jelly'in sözlüğünün burada kullanılan 'Kennesaw' (Atlanta, Georgia'nın kuzeybatısında bir şehir) gibi bir kelimesi olduğu gerçeğini seviyorum, çünkü burada endeksleme [5, 1, -5, -1] + 1yapıyor nesw!

açıklama

“þ...e’                    | Base-250 integer 1962789844189344852  
       b6                  | Convert to base 6 (2, 2, 5, 2, 5, 0, 2, 2, 5, 3, 3, 0, 2, 2, 3, 0, 2, 0, 2, 0, 3, 0, 2, 0)
         Ḥ                 | Double
          _5               | Subtract 5
            Ż              | Prepend 0
             ⁸  ¥Ƭ         | Using this as the right argument and the original link argument as the left argument, loop the following as a dyad until there is no change, collecting up results
              +            | - Add the left argument to:
               ị           |   - The left argument indexed into the right argument
                  I        | Differences between consecutive numbers
                   ‘       | Increment by 1
                    ị“®ȯẹ» | Index into "Kennesaw"

2

PHP , 110 bayt

Chas Brown'un harika cevabı ya da xnor'ın harika cevabı olmayan bir çözüm . Bunun daha uzun olduğunu biliyorum ama farklı bir çözüm bulmak istedim!

for($n=$argn;$n>1;$n=ord($s[$n*2+1])%30)echo($s='0000w<w sEw"s)n w%w&s-e*e+n&w+w,e/n*w/n,w1n.e5n0w5n2')[$n*2];

Çevrimiçi deneyin!

Tahtadaki her hücre için 2 karakterden oluşan bir eşleme dizesi oluşturdum. Her hücre için ilk karakter bir harekettir (n / e / s / w) veya 0ikinci karakterin ASCII kodu mod 30, hücreden ( cell < 2) çıkana kadar hareketini tekrarlamalı modda izlememiz gereken başka bir hücre numarası döndürür .

Örneğin 8 girişi için:

  • Hücre için 2 karakter 8:w%
  • wHücrenin baskılarını ve hareketlerini sürdürmek anlamına gelir .%
  • %Mod 30'un 7 olacağı ASCII kodu 37'dir, bu nedenle takip edilecek bir sonraki hücredir 7.
  • Hücre için 2 karakter 7şunlardır: n (son karakter boşluk, ASCII kodu = 32)
  • Baskı nve 32 mod 30 hücresi için hamle ile devam etmek anlamına gelir 2.
  • Hücre için 2 karakter 2şunlardır: w<(son karakter ASCII kodu = 60)
  • Bu, baskı wve 60 mod 30 hücresi için hamle ile devam etmek anlamına gelir 0.
  • Hücre sayısı küçükse 2, döngü durur!
  • Nihai basılı sonuç: wnw

PHP , 75 bayt

Bu sürüm Grimy tarafından yazılmıştır , daha akıllı olduğu için orijinal cevabımdan 35 bayt daha kısadır! Grimy'nin yorumu: "4 * 25 <256, yani hücre başına sadece 1 bayta ihtiyacınız var, 2 değil"

for($n=$argn;$n=ord("0\0~f;6o4R:s%ql&rup*@^tIDbx"[$n%25]);)echo news[$n%4];

Çevrimiçi deneyin!


PHP , 71 bayt

Bu liman Arnauld cevabı limanı olan XNOR cevabı çıkıyor beri, ama bir döngü yerine özyinelemeli fonksiyonu olarak PHP daha kısa olması.

for($n=$argn;--$n;$n+=$d*3+$d%2-4)echo nwes[$d=79459389361621/4**$n&3];

Çevrimiçi deneyin!


2
4 * 25 <256, bu yüzden hücre başına sadece 1 bayta ihtiyacınız var, 2 değil: Çevrimiçi deneyin!
Grimmy

1
@Grimy, şaşırtıcı, sanırım ayrı bir cevap olarak göndermelisin, yeterince farklı.
Gece2

1
Bunu yapmayacağım, bu yüzden cevabınıza dahil etmeyi veya sadece bir yorum olarak bırakmayı seçersiniz.
Grimmy

1
@ Grimy, sürümünüzü adınızla ekledi. Yine de teşekkürler.
Gece2

2

C (clang) , 81 bayt

v;f(p){p-1&&putchar(v="00wwswsnwwseenwwenwnwnenwn"[p])+f(p+=v%5?6-v%8:v%2?5:-5);}

Çevrimiçi deneyin!

@ Tommylee2k önerisi -8 sayesinde! + özyinelemeli çağrı

C (clang) , 90 bayt

v;f(p){for(char*l="00wwswsnwwseenwwenwnwnenwn";p-1;p+=v%5?6-v%8:v%2?5:-5)putchar(v=l[p]);}

Çevrimiçi deneyin!

Sıkıştırılmamış tüm çözümlere benzer.


1
kısaltılabilir:v;f(p){for(;p-1;p+=v%5?6-v%8:v%2?5:-5)putchar(v="00wwswsnwwseenwwenwnwnenwn"[p]);}
Tommylee2k

1

05AB1E , 45 43 bayt

õ?[Ð#.•DUo¢ê`Ω÷‰₂¡)R€ûK•¦sè©?Ž₁9₂в6-'€Ã®kè+

Bağlantı noktası @ChasBrown 's Python 2 cevabı .

Çevrimiçi deneyin veya tüm test senaryolarını doğrulayın .

Açıklama:

õ?               # Output an empty string
                 # (to overwrite the implicit output if the input is 1)
[                # Start an infinite loop:
 Ð               #  Triplicate the top of the stack
                 #  (which is the (implicit) input in the first iteration)
  #              #  If it's exactly 1: stop the infinite loop
  .•DUo¢ê`Ω÷‰₂¡)R€ûK
                 #  Push compressed string "a  wwswsnwwseenwwenwnwnenwn"
   ¦             #  Remove the first character
    sè           #  Swap to get the number, and use it to index into the string
      ©          #  Store it in variable `®` (without popping)
       ?         #  Print it without trailing newline
  Ž₁9            #  Push compressed integer 22449
     ₂в          #  Convert to base-26 as list: [1,7,5,11]
       6-        #  Subtract 6 from each: [-5,1,-1,5]
         '€Ã    '#  Push dictionary string "news"
            ®k   #  Get the index in this string of character `®`
              è  #  And use that to index into the integer-list
               + #  And add it to the originally triplicated integer

Neden .•DUo¢ê`Ω÷‰₂¡)R€ûK•olduğunu anlamak için bu 05AB1E ucuma (dört bölümün tümü) bakın"a wwswsnwwseenwwenwnwnenwn" ; Ž₁9olduğu 22449; Ž₁9₂вolduğu [1,7,5,11]; ve '€Ãöyle "news".


1
Bu uygun sözlük dizesi iyi haber olmalı!
Neil

@Neil Kesinlikle. :) Görünüşe göre sözlük dizesi westerndaha iyidir. ; p
Kevin Cruijssen

1

Bash , 120 bayt

S=__wwswsnwwseenwwenwnwnenwn
N=n-5w-1s05e01
for((i=$1;$i>1;i+=$j)){ d=${S:$i:1};j=${N:`expr index $N $d`:2};printf $d; }

Çevrimiçi deneyin!

Dizeyi nibble olarak bit paketlemeye çalışırken bir süre oynadım, ancak kod çözme kaydedilen sayıdan daha fazla karakter gerektiriyordu.

Nasıl çalışır:

S=__wwswsnwwseenwwenwnwnenwn

$ S dizesi, her oda için bir odayı çıkışa doğru hareket ettirmek için hangi yöne gidileceğini gösteren ve 0 ve 1 odalarını atlayan tek bir karakter (n, w, s, e) içerir.

N=n-5w-1s05e01

$ N dizesi, her yön değişikliği için geçerli oda numarasına eklenecek / çıkarılacak deltaya sahiptir (n: -5, w: -1, s: +5, e: +1)

for((i=$1;$i>1;i+=$j)){ d=${S:$i:1};j=${N:`expr index $N $d`:2};printf $d; }

$ İ ile komut satırında verilen oda numarasına eşittir ($ 1). $ S dizinindeki $ i dizinindeki karakteri $ d dizinine atayın. Sonraki odaya götürülecek yön için $ j'den delta değerini alın ve $ j'ye atayın.

$ D almak için bir sonraki yönü yazdırın.

$ J içindeki deltayı $ i'ye / den i'den çıkarın.

Biz oda # 2 ($ i> 1 iken) ayrılana kadar döngü.



Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.