บอลแรงโน้มถ่วง


33

คุณอยู่ในสถานีอวกาศอวกาศขั้นสูง เพื่อนของคุณที่กำลังฝึกฝนในการศึกษาเรื่องแรงโน้มถ่วงเพิ่งสร้างเกมที่เกี่ยวข้องกับการใช้ microgravity เป็นวิธีในการเคลื่อนลูกบอล

เธอส่งคอนโทรลเลอร์ขนาดเล็กให้คุณพร้อมลูกศรสี่ทิศทางที่อยู่บนเขาและเขาวงกตเหมือนโครงสร้างที่มีลูกนั่งอยู่ทางซ้าย เธอเริ่มอธิบายว่าเกมทำงานอย่างไร

  • คุณมี 2 ปุ่มทิศทางซ้ายและขวา<>
  • คุณมีปุ่มแรงโน้มถ่วง 2 ปุ่มขึ้น^และลงv(อย่างน้อยจากเฟรมอ้างอิงของคุณ)
  • คุณจะใช้ปุ่มลูกศรเหล่านี้เพื่อย้ายลูกบอลไปรอบ ๆ บนหน้าจอของคุณ

"ตอนนี้มีกฎบางอย่างที่ต้องปฏิบัติตาม" เธอพูดว่า

  1. แพลตฟอร์มทั้งหมดจะต้องถูกสำรวจก่อนที่จะถึงถ้วย \ /
  2. ลูกศร< > ^ vจะถูกใช้เพื่อระบุการเคลื่อนไหวของลูกบอล
  3. แรงโน้มถ่วงคือ^ v(ขึ้นและลง) สิ่งนี้จะทำให้ลูกบอลเคลื่อนที่ไปสู่แพลตฟอร์มถัดไปในทิศทางนั้น (ไม่คำนวณระยะทางสำหรับขึ้นและลง)
  4. การสูญเสียลูกไม่ดี! อย่าล้มลงบนขอบและอย่าสลับแรงโน้มถ่วงเร็วเกินไปจนลูกบอลของคุณไม่ถึงแพลตฟอร์ม
  5. การเคลื่อนไหวถูกนับเป็นขั้นตอนของ < >
  6. ลูกบอลสามารถเข้าสู่ถ้วยได้จากทุกทิศทางตราบใดที่มีการปฏิบัติตามกฎข้อ 1
  7. คุณต้องระบุทิศทางของแรงโน้มถ่วงเพื่อให้ลูกบอลของคุณไม่ลอยไป
  8. การเคลื่อนไหวอาจมีการสุ่มตราบเท่าที่กฎข้อ 1 และกฎ 4 เป็นไปตาม
  9. สำหรับกรณีที่ไม่สามารถแก้ไขเอาต์พุตเท็จหรือไม่ถูกต้อง

ตัวอย่างง่ายๆของลูกบอลแพลตฟอร์มและถ้วย:

v
o
---\ /

v>

 o
---\ /

v>>

  o
---\ /

v>>>

   o
---\ /

v>>>>


---\o/

ตัวอย่างการข้ามผ่านแพลตฟอร์มเดียวกันอีกครั้ง

v    

 o
 ----

\ /-------

v>   

  o
 ----

\ /-------

v>>

   o
 ----

\ /-------

v>>>

    o
 ----

\ /-------

v>>>>


 ----
     o
\ /-------

v>>>>>


 ----
      o
\ /-------

v>>>>>>


 ----
       o
\ /-------

v>>>>>>>


 ----
        o
\ /-------

v>>>>>>>>


 ----
         o
\ /-------

v>>>>>>>><<<<<<<< # move all the way to the left to get to the cup


 ----

\o/-------

ตัวอย่างของการสลับแรงโน้มถ่วง

v
   --/ \

o
----

v>
   --/ \

 o
----

v>>
   --/ \

  o
----

v>>>
   --/ \

   o
----

v>>>^
   --/ \
   o

----

v>>>^>
   --/ \
    o

----

v>>>^>>
   --/ \
     o

----

v>>>^>>>
   --/o\


----

งาน

งานของคุณคือการสร้างโปรแกรมที่จะเป็นตัวแทนของหลักสูตร ASCII เป็นอินพุต และเอาท์พุทลูกศรที่<>^vแสดงทิศทางและแรงโน้มถ่วงเพื่อย้ายลูกบอลoข้ามสิ่งทั้งหมดplatformsลงในถ้วย

บังคับใช้กฎกอล์ฟมาตรฐาน

กรณีทดสอบ

อินพุต (สถานการณ์ที่มีการสลับแรงโน้มถ่วง)

         ----   --/ \
---    --
o

  ------    -----

เอาท์พุต

^>>v>>>>>^>>>>>v>>>>^>>>

ป้อนคำอธิบายรูปภาพที่นี่


อินพุต (สถานการณ์ที่เปลี่ยนทิศทาง)

       ---
o   
----
    ---

     -----  

    --\ /

เอาท์พุต

v>>>>>>^>>>v<<<<<v>>>

ป้อนคำอธิบายรูปภาพที่นี่


อินพุต (สถานการณ์ที่คุณต้องข้ามผ่านแพลตฟอร์มเดียวกันสองครั้ง)

 o
 ------

  ------

 ------ 

\ /------

เอาท์พุต

v>>>>>><<<<<<>>>>>>><<<<<<

ป้อนคำอธิบายรูปภาพที่นี่


กรณีไม่ถูกต้องโปรแกรมควรส่งออกเท็จสำหรับสิ่งเหล่านี้

ไม่มีทางที่ลูกบอลจะไปสู่แพลตฟอร์มต่อไปได้

o
--- ---

บอลจะลอยออกไปสู่อวกาศ

---
o
   ---

สถานการณ์ที่ลูกบอลเข้ามาในถ้วย แต่ทุกแพลตฟอร์มไม่ได้เคลื่อนที่

o
----
    ----
        \ /----

4
กฎข้อที่ 1 ทำให้เรื่องนี้ค่อนข้างท้าทาย ... อืม ...
จองฮันมิน

ปริศนาจะสามารถแก้ไขได้เสมอหรือไม่ นอกจากนี้ฉันคิดว่าคุณควรรวมกรณีทดสอบที่ต้องใช้การย้อนรอย
FryAmTheEggman

ใช่ปริศนาควรได้รับการแก้ไขเสมอ ช่องว่างหรือการกระโดดที่เสียบอลหรือสถานการณ์ที่ทำให้เขาไม่สามารถแก้ตัวไม่ได้
tisaconundrum

4
@JungHwanMin กฎข้อที่ 1 เป็นเหตุผลว่าทำไมนี่จึงเป็นความท้าทายและไม่น่ารำคาญ
Erik the Outgolfer

2
ฉันไม่เคยรู้สึกถึงหลุมกระต่ายในคำถาม
codegolf เลย

คำตอบ:


11

Pyth, 431 ไบต์

นี่เป็นโปรแกรม Pyth แรกของฉัน (อันที่จริงนี่เป็นโปรแกรมแรกของฉันในภาษาโค้ดกอล์ฟใด ๆ ) ซึ่งหมายความว่ามันอาจจะปรับปรุงได้

Jmmck\:cd\%c.Z"xÚU±Ã@DÅ W,J áDPáÒ­V`ýüw{g$ÍÀÞÇr§o.÷å8èÝÇr{øºy{~1åõ:noßÃú/.yçíäÂ'ëL¢êF¸èÆ\ka´QÒnÒ@tãÒÁµÆ¾õö»bÍH¥¦$¨%5Eyîÿ}ó§ûrh³oÄåËÄqõ XÔHû"\_KYDrGHFN@JGIn=bm:d.*NHHRb)RHDiNTR.turNG.tT;M:jH)hh@JG0DXGHN=Ti+3qG\^HI!},GTK aK,GT aY+eKNI&!g5T}\EjT)N.q;D(GHNT)INIqHhT=ZrGhtTInZhtTXHZ+eTN))).?I&nHhTgGhtTXHhtT+eTH; aK,di2i1r0.z aY+eKk#=N.(Y0(6\vkN)(7\^kN)(8\v\<N)(9\v\>N)(10\^\<N)(11\^\>N

ลองที่นี่ (testcase ล่าสุดต้องใช้เวลานานเกินไปจะต้องทดสอบด้วยการติดตั้ง Pyth แบบท้องถิ่น)

Hex dump ของรหัส (ใช้xxd -r <filename>เพื่อถอดรหัส):

00000000: 4a6d 6d63 6b5c 3a63 645c 2563 2e5a 2278  Jmmck\:cd\%c.Z"x
00000010: da55 8eb1 8ac3 400c 447f c58d 2057 2c99  .U....@.D... W,.
00000020: 4aa0 e144 50e1 d2ad 5660 87fd 84fc 7f77  J..DP...V`.....w
00000030: 7b67 1f24 cdc0 8319 de1c c772 a76f 2ef7  {g.$.......r.o..
00000040: e538 e8dd c772 7bf8 9eba 797b 7e31 e5f5  .8...r{...y{~1..
00000050: 8e3a 6e8f 6fdf c3fa 2f2e 0c79 e717 ede4  .:n.o.../..y....
00000060: c21f 27eb 8395 189a 4c15 140b a28d ea82  ..'.....L.......
00000070: 46b8 e8c6 5c05 1b6b 1d61 b490 0251 d28c  F...\..k.a...Q..
00000080: 6ed2 4087 74e3 1ad2 c1b5 c6be f5f6 1cbb  n.@.t...........
00000090: 6286 cd48 a5a6 24a8 2535 4579 eeff 7df3  b..H..$.%5Ey..}.
000000a0: 8a8a 1613 a7fb 7204 68b3 6fc4 e51b 160c  ......r.h.o.....
000000b0: 1304 cbc4 8a71 f57f 2058 d448 fb22 5c5f  .....q.. X.H."\_
000000c0: 4b59 4472 4748 464e 404a 4749 6e3d 626d  KYDrGHFN@JGIn=bm
000000d0: 3a64 2e2a 4e48 4852 6229 5248 4469 4e54  :d.*NHHRb)RHDiNT
000000e0: 522e 7475 724e 472e 7454 3b4d 3a6a 4829  R.turNG.tT;M:jH)
000000f0: 6868 404a 4730 4458 4748 4e3d 5469 2b33  hh@JG0DXGHN=Ti+3
00000100: 7147 5c5e 4849 217d 2c47 544b 2061 4b2c  qG\^HI!},GTK aK,
00000110: 4754 2061 592b 654b 4e49 2621 6735 547d  GT aY+eKNI&!g5T}
00000120: 5c45 6a54 294e 2e71 3b44 2847 484e 5429  \EjT)N.q;D(GHNT)
00000130: 494e 4971 4868 543d 5a72 4768 7454 496e  INIqHhT=ZrGhtTIn
00000140: 5a68 7454 5848 5a2b 6554 4e29 2929 2e3f  ZhtTXHZ+eTN))).?
00000150: 4926 6e48 6854 6747 6874 5458 4868 7454  I&nHhTgGhtTXHhtT
00000160: 2b65 5448 3b20 614b 2c64 6932 6931 7230  +eTH; aK,di2i1r0
00000170: 2e7a 2061 592b 654b 6b23 3d4e 2e28 5930  .z aY+eKk#=N.(Y0
00000180: 2836 5c76 6b4e 2928 375c 5e6b 4e29 2838  (6\vkN)(7\^kN)(8
00000190: 5c76 5c3c 4e29 2839 5c76 5c3e 4e29 2831  \v\<N)(9\v\>N)(1
000001a0: 305c 5e5c 3c4e 2928 3131 5c5e 5c3e 4e    0\^\<N)(11\^\>N

คำอธิบาย

แนวคิดหลักสำหรับโปรแกรมนี้คือการใช้นิพจน์ทั่วไปเพื่อแก้ไขอินพุต เพื่อประหยัดพื้นที่นิพจน์ทั่วไปเหล่านี้ทั้งหมดจะอยู่ในสตริงที่บีบอัด ขั้นตอนแรกในโปรแกรมคือการคลายการบีบอัดสตริงและเพื่อแยกการแสดงออกปกติ int เดียวและสตริงการแทนที่ที่สอดคล้องกัน

            .Z"..."     Decompress the string
           c       \_   Split the result into pieces (separator is "_")
  m    cd\%             Split all pieces (separator is "%")
 m ck\:                 Split all sub-pieces (separator is ":")
J                       Assign the result to variable J

เนื้อหาของตัวแปรJคือ:

[[['\\\\ /', '=M='], ['/ \\\\', '=W=']],
 [[' (?=[V6M=-])', 'V'], ['o(?=[V6M=-])', '6']],
 [['(?<=[A9W=-]) ', 'A'], ['(?<=[A9W=-])o', '9'], ['(?<=[X0W=-])V', 'X'], ['(?<=[X0W=-])6', '0']],
 [['6V', 'V6'], ['0X', 'X0'], ['6-', '6='], ['0-', '0='], ['6M', 'VE'], ['0M', 'XE']],
 [['A9', '9A'], ['X0', '0X'], ['-9', '=9'], ['-0', '=0'], ['W9', 'EA'], ['W0', 'EX']],
 [['[MW-]']],
 [['[60]']],
 [['[90]']],
 [['V6', '6V'], ['V0', '6X'], ['X6', '0V'], ['X0', '0X']],
 [['6V', 'V6'], ['0V', 'X6'], ['6X', 'V0'], ['0X', 'X0']],
 [['A9', '9A'], ['A0', '9X'], ['X9', '0A'], ['X0', '0X']],
 [['9A', 'A9'], ['0A', 'X9'], ['9X', 'A0'], ['0X', 'X0']]]

KY   Set the variable K to an empty list

ฟังก์ชั่นrใช้แทน regex จากรายการที่เก็บไว้ในJที่ดัชนีสตริงทั้งหมดในรายการG Hมันจะส่งกลับทันทีที่มีการเปลี่ยนแปลงสตริง

DrGH                         Define the function r(G,H)
    FN@JG              )     Loop for all entries in J[G]
             m:d.*NH         Regex substitution, replace N[0] with N[1] in all strings in list H
           =b                Store the result in variable b
         In         HRb      If b != H return b
                        RH   Return H

ฟังก์ชั่นiนี้คล้ายกับฟังก์ชั่นที่rมี 2 ​​ข้อแตกต่าง มันใช้การทดแทนในรายการ transposed (แนวตั้งแทนแนวนอน) มันยังทำการทดแทนซ้ำ ๆ ตราบใดที่มีการเปลี่ยนแปลง

DiNT          ;   Define the function i(N,T)
           .tT    Transpose the list T
       urNG       Apply r(N,...) repeatedly as long as something changes
    R.t           Transpose the result back and return it

ฟังก์ชั่นgการตรวจสอบถ้า regex จากรายการที่เก็บไว้ในJที่ดัชนีGสามารถพบได้โดยในสตริงใด ๆ Hในรายการ

M             Define the function g(G,H)
     hh@JG    Get the single regex stored in J[G]
  jH)         Join all strings in H
 :        0   Check if the regex is found anywhere in the joined string

ส่วนที่เหลือของรหัสประกอบด้วยตรรกะของโปรแกรมจริง มันทำการค้นหาความกว้างก่อนสำหรับการเคลื่อนไหวที่เป็นไปได้จนกว่าจะพบวิธีแก้ปัญหา ตำแหน่งในแผนผังการค้นหาจะถูกกำหนดโดยทิศทางของแรงโน้มถ่วงและสำเนาที่แก้ไขแล้วของอินพุตโปรแกรม Kเพื่อหลีกเลี่ยงการประมวลผลของตำแหน่งเดียวกันอีกครั้งและอีกครั้งในตำแหน่งการประมวลผลจะถูกเก็บไว้ในรายการระดับโลก Yตำแหน่งซึ่งยังคงต้องได้รับการประมวลผลจะถูกเก็บไว้ร่วมกับส่วนที่เกี่ยวข้องของการแก้ปัญหาในรายการ

การปรับเปลี่ยนอินพุตและการกำหนดค่าเริ่มต้นของKและYดำเนินการโดยรหัสต่อไปนี้:

           .z          Get all input as a line list
     i2i1r0            Apply the regular expressions stored in J[0] horizontally, and the the ones from J[1] and J[2] vertically
   ,d                  Create a list with " " (represents "no gravity set") and the modifed input
 aK                    Append the result to the list K
                 eK    Retrieve the appended list again
                +  k   Append "" to the list (represents the empty starting solution)
              aY       Append the result to the list Y

การปรับเปลี่ยนอินพุตทำสิ่งต่อไปนี้ อินพุต:

         ----   --/ \
---    --
o

  ------    -----

เปลี่ยนเป็น:

VVVVVVVVV----VVV--=W=
---VVVV--AAAXVVVXAAAA
9AXVVVVXAAAAXVVVXAAAA
AAXVVVVXAAAAXVVVXAAAA
AA------AAAA-----AAAA

ค่ามีความหมายต่อไปนี้:

  • - แพลตฟอร์มที่ต้องเข้าชม
  • = แพลตฟอร์มที่ไม่จำเป็นต้องเยี่ยมชมอีกต่อไป
  • M คัพซึ่งสามารถป้อนด้วยแรงโน้มถ่วงตั้งค่าเป็น "ลง"
  • W ถ้วยซึ่งสามารถป้อนได้ด้วยแรงโน้มถ่วงที่ตั้งค่าเป็น "up"
  • V ปลอดภัยที่จะย้ายไปยังสถานที่แห่งนี้ด้วยแรงโน้มถ่วงที่กำหนดเป็น "ลง"
  • A ปลอดภัยที่จะย้ายไปยังสถานที่นี้โดยตั้งค่าแรงโน้มถ่วงเป็น "ขึ้น"
  • X ปลอดภัยที่จะย้ายมาที่นี่โดยไม่คำนึงถึงแรงโน้มถ่วง
  • 6 ลูกบอลในสถานที่ซึ่งจะถูกทำเครื่องหมายเป็น V
  • 9 ลูกบอลในสถานที่ซึ่งจะถูกทำเครื่องหมายเป็น A
  • 0 ลูกบอลในสถานที่ซึ่งจะถูกทำเครื่องหมายเป็น X

ตรรกะใช้การแสดงออกปกติเพื่อทำการเคลื่อนไหว ในตัวอย่างด้านบนหากแรงโน้มถ่วงถูกตั้งค่าเป็น "up" เราสามารถแทนที่ "9A" ด้วย "A9" ด้วย regex เพื่อย้ายลูกบอลไปทางขวา ซึ่งหมายความว่าโดยพยายามใช้ regex เราสามารถค้นหาการเคลื่อนไหวที่เป็นไปได้ทั้งหมด


ฟังก์ชั่นนี้Xดำเนินการเคลื่อนที่ของลูกบอลแนวตั้งตามการตั้งค่าแรงโน้มถ่วงในปัจจุบันจัดเก็บผลลัพธ์ในรายการส่วนกลางKและYและตรวจสอบว่าพบวิธีแก้ปัญหาหรือไม่

DXGHN                                             ;   Define the function X(G,H,N)
        +3qG\^                                        Select the correct set of regular expressions based on the current gravity setting G (3 for "v" and 4 for "^")
     =Ti      H                                       Apply i(...,H) and store the result in T 
               I!},GTK                                If [G,T] not in K
                       aK,GT                          Store [G,T] in K 
                             aY+eKN                   Store [G,T,N] in Y 
                                   I&!g5T}\EjT)       If J[5] not found in T and T contains "E" (all platforms visited and ball in cup)
                                               N.q    Print N and exit

ฟังก์ชั่นนี้(ใช้ตรวจสอบปุ่ม 4 ทิศทาง / แรงโน้มถ่วง ปุ่มแรงโน้มถ่วงสามารถกดได้ก็ต่อเมื่อแรงโน้มถ่วงในปัจจุบันเปลี่ยนไปและหากลูกบอลอยู่ในที่ปลอดภัยเพื่อเปลี่ยนแรงโน้มถ่วง สามารถกดปุ่มทิศทางได้ก็ต่อเมื่อปลอดภัยที่จะย้ายไปยังตำแหน่งที่เกี่ยวข้อง

D(GHNT)                                                    ;   Define the function ( (G,H,N,T)
       IN                           )                          If N is not empty (contains either "<" or ">" representing directional buttons)
         IqHhT                     )                           If H (gravity setting for which this test is performed) is equal T[0] (the current gravity)
              =ZrGhtT                                          Apply r(G,T[1]) and store the result in Z (G is the appropriate regex index for the combination of gravity and directional button, T[1] is the current modified input) 
                     InZhtT       )                            If Z != T[1] (the regex operation changed something, meaning we found a valid move)
                           XHZ+eTN                             Call X(H,Z,[T[2],N]) 
                                     .?                        Else (gravity button pressed)
                                       I                       If ...
                                         nHhT                  H (new gravity setting) is not equal T[0] (current gravity setting) 
                                        &                      ... and ...
                                             gGhtT             J[G] found in T[1] (ball is in an appropriate place to switch gravity) 
                                                  XHhtT+eTH    Call X(H,T[1],[T[2],H])

ในที่สุดห่วงหลัก องค์ประกอบแรกของYจะถูกลบออกซ้ำ ๆ และตรวจสอบการเคลื่อนไหวที่เป็นไปได้ทั้งหมดจะดำเนินการ

#                                                        Loop until error (Y empty)
 =N.(Y0                                                  Pop first element of Y and store it in the variable N
       (6\vkN)                                           Call ( (6,"v","",N)
              (7\^kN)                                    Call ( (7,"^","",N)
                     (8\v\<N)                            Call ( (8,"v","<",N)
                             (9\v\>N)                    Call ( (9,"v",">",N)
                                     (10\^\<N)           Call ( (10,"^","<",N)
                                              (11\^\>N   Call ( (11,"^",">",N)

ฉันคิดถูกแล้วว่าคุณคิดว่าทุกอินพุตนั้นแก้ไขได้? เนื่องจากคำถามยังระบุว่าควรตรวจพบอินพุตที่ไม่สามารถแก้ไขได้อย่างไรก็ตามความคิดเห็นแสดงให้เห็นว่าอินพุตทุกรายการจะสามารถแก้ไขได้ ฉันไม่แน่ใจซึ่งเป็นกรณีนี้ แต่ฉันคิดว่ารหัสของคุณไม่สามารถตรวจพบการแก้ไม่ได้
Jonathan Frech

@JonathanFrech หากอินพุตไม่สามารถแก้ไขได้จะไม่มีเอาต์พุต เมื่อตรวจสอบความเป็นไปได้ทั้งหมดYรายการจะว่างเปล่าป๊อปจะโยนข้อผิดพลาดและ#วนรอบจะสิ้นสุด
Sleafar

1
เมื่อคุณนำถ้วยออกจากอินพุต (`/ \ ') ปริศนาจะไม่สามารถแก้ไขได้ (เนื่องจากคุณไม่สามารถเข้าถึงถ้วยได้) แต่โปรแกรมของคุณยังคงสร้างเอาต์พุต
Jonathan Frech

ฉันไม่ได้หมายความว่าโปรแกรมของคุณทำอะไรฉันระบุว่าปริศนาตัวต่อที่แก้ไม่ได้นี้สร้างผลลัพธ์
Jonathan Frech

@JonathanFrech คุณพูดถูก ฉันแค่พยายามแก้ไข แต่ฉันมีปัญหาการเข้ารหัสกับสตริงที่บีบอัด
Sleafar
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.