การผจญภัยนักกอล์ฟ - บทที่ 1: แจกัน


13

ผจญภัยนักกอล์ฟ

นี่คือความท้าทายแรก! จะมีความท้าทายเพิ่มเติมในภายหลังที่จะต้องใช้ข้อมูลจากการท้าทายครั้งก่อน :)

บทที่ 1: แจกัน

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

ความท้าทายแรกของคุณคือการช่วยหมู่บ้านเล็ก ๆ น้อย ๆ ปีศาจก็เต็มใจที่จะไม่ทำลายหมู่บ้านทั้งหมู่บ้านหากคุณแก้ปัญหาความท้าทายของเขา

ความท้าทาย:

คุณมีแจกันแนวตั้งซึ่งมีได้ทั้งหมด 10 อย่าง (รวมอยู่ในอากาศ) หากคุณใส่สิ่งของลงในแจกันนั้นแรงโน้มถ่วงจะทำให้สิ่งนั้นตกลงไปด้านล่าง หากแจกันเต็มแล้ว (และเต็มถ้าคุณคิดว่าเป็น "เต็มอากาศ") อินพุตจะแทนที่องค์ประกอบที่ด้านบนของแจกัน

นี่คือชุดของสิ่งต่าง ๆ ที่ได้รับอนุญาต:

  • อากาศ 0 /
  • ร็อค 1 / -
  • ใบไม้ 2 / ~
  • ระเบิด 3 / x

หากมีหินหรือใบไม้อยู่ด้านบนของ "ระเบิด" มันจะระเบิดและทำลายสิ่งที่อยู่ด้านบนของมัน

การป้อนข้อมูลคือรายการของสิ่งที่คุณจะใส่ในแจกันทุกเทิร์น

ตัวอย่าง: 11231: คุณจะใส่หิน 2 ก้อนจากนั้นใบไม้จากนั้นระเบิดและในที่สุดก็เป็นหินก้อนสุดท้าย

เมื่อแจกันคงที่คุณสามารถเริ่มนับด้วยกฎต่อไปนี้:

  • Rock เพิ่ม 1 ยูนิตไปยังตัวสะสม
  • ใบไม้คูณตัวสะสมด้วย 2
  • ระเบิดจะลดการสะสม 1
  • อากาศไม่ทำอะไรเลย

(คุณต้องเริ่มนับจากส่วนบนของแจกัน)

นี่คือการจำลองที่เราใช้ "11231" เป็นอินพุต:

|-|  |-|  |~|  |x|  |-|  | |  | |  | |  | |  | |  | |
| |  |-|  |-|  |~|  |x|  |-|  | |  | |  | |  | |  | |
| |  | |  |-|  |-|  |~|  |x|  |-|  | |  | |  | |  | |
| |  | |  | |  |-|  |-|  |~|  |x|  |-|  | |  | |  | |
| |  | |  | |  | |  |-|  |-|  |~|  |x|  |-|  | |  | |
| |  | |  | |  | |  | |  |-|  |-|  |~|  |x|  |-|  | |
| |  | |  | |  | |  | |  | |  |-|  |-|  |~|  |x|  | |
| |  | |  | |  | |  | |  | |  | |  |-|  |-|  |~|  |~|
| |  | |  | |  | |  | |  | |  | |  | |  |-|  |-|  |-|
| |  | |  | |  | |  | |  | |  | |  | |  | |  |-|  |-|

และผลลัพธ์จะเป็น 2 (คำนวณเป็น((0 x 2) + 1) + 1) ไม่จำเป็นต้องพิมพ์สถานะทั้งหมดของแจกัน!

โปรแกรมพื้นฐาน (Python3)

คุณสามารถรันมันเพื่อทำความเข้าใจว่ามันทำงานอย่างไร

def printVase(vase):
  for i in vase:
    if i == 1:
      print("|-|")
    elif i == 2:
      print("|~|")
    elif i == 3:
      print("|x|")
    else:
      print("| |")

def updateVase(vase):
  changed = False
  for i in range(len(vase), -1, -1):
    if i < len(vase) - 1:
      if vase[i+1] == 3 and vase[i] in [1,2]:
        vase[i], vase[i+1] = 0, 0
        changed = True
      if not vase[i+1] and vase[i] in [1, 2, 3]:
        vase[i], vase[i+1] = vase[i+1], vase[i]
        changed = True
  return changed

userInput = input("Vase : ")
vase = [0 for i in range(0, 10)]
oldVase = vase
while updateVase(vase) or userInput != "":
  if userInput != "":
    vase[0] = int(userInput[0])
  userInput = userInput[1::]
  printVase(vase)
  input()

accumulator = 0
for i in vase:
  if i == 1:
    accumulator += 1
  if i == 2:
    accumulator *= 2
  if i == 3:
    accumulator -= 1
print(accumulator)

รุ่นที่ตีกอล์ฟ (Python3, ไม่มีการแสดงแจกัน): 360 ไบต์ = 360 คะแนน

def u(v):
  c=0
  for i in range(len(v),-1,-1):
    if i<len(v)-1:
      if v[i+1]==3 and v[i]in[1,2]:v[i],v[i+1],c=0,0,1
      if not v[i+1]and v[i]in[1,2,3]:v[i],v[i+1],c=v[i+1],v[i],1
  return c
l,v=input(),[0 for i in range(0, 10)]
while u(v)or l!="":
  if l!="":v[0],l=int(l[0]),l[1::]
a=0
for i in v:
  if i==1:a+=1
  if i==2:a*=2
  if i==3:a-=1
print(a)

หากคุณต้องการทดสอบว่าโปรแกรมของคุณทำงานอย่างถูกต้องหรือไม่คุณสามารถทดสอบอินพุตนี้: 12122111131

คำตอบที่ถูกต้องคือ 43 :) (ขอบคุณ Emigna)

ตอนนี้สำหรับคะแนน:

  • (x) จุดที่: x คือจำนวนไบต์ที่จำเป็นในการเขียนโปรแกรมของคุณ หากคุณตอบหลังจากที่มีการโพสต์ความท้าทายครั้งต่อไปคะแนนสำหรับความท้าทายนี้จะไม่ถูกเพิ่มเข้าไปในจำนวนคะแนนรวมของคุณ

เป้าหมายคือการเก็บคะแนนขั้นต่ำในระหว่างการท้าทายทั้งหมด :) หากคุณข้ามส่วนใดส่วนหนึ่งของการแข่งขันคุณจะมี (wx + 1) คะแนนโดยค่าเริ่มต้นสำหรับส่วนที่ถูกข้าม (โดยที่ wx คือคะแนนที่แย่ที่สุด สำหรับความท้าทายนั้น)

ข้อมูลที่จำเป็นสำหรับการท้าทายครั้งต่อไป:

เอาต์พุตเมื่ออินพุต = 10100000200310310113030200221013111213110130332101

แชมป์ปัจจุบัน: Emigna

โชคดีนะทุกคน !


2
มีอะไรใน "สามารถมี 10 สิ่งที่แน่นอน"? "อากาศ" นับเป็นสิ่งหรือไม่? มีการรับประกันอินพุตหรือไม่ว่าแจกันจะมีเพียง 10 อย่างเท่านั้น (ฉันไม่เห็นว่ารองรับในการนำไปใช้อ้างอิง) นอกจากนี้อินพุทที่สร้างข้อมูลสำหรับความท้าทายครั้งต่อไปนั้นดูเหมือนจะมีมากกว่า 10 สิ่ง (แม้ว่าอากาศจะไม่เป็นอะไรเลยและระเบิดก็ระเบิดสิ่งต่อไปที่ด้านบนของอากาศจะมี 14 สิ่ง)
Jonathan Allan

1
อินพุท333สร้างแจกัน[0, 0, 0, 0, 0, 0, 0, 3, 3, 3]ในอัลกอริทึม golfed ของคุณและด้วยคะแนน-3แต่ไม่ควร[0, 0, 0, 0, 0, 0, 0, 0, 0, 3]และจากนั้นคะแนน-1ตามสเปคของคุณ?
Laikoni

2
@Laikoni ฉันลืมที่จะระบุว่าระเบิดไม่ระเบิดเมื่อวางระเบิดอยู่ด้านบนของอีกคนหนึ่งขอบคุณ!
Sygmei

1
เอาต์พุตสำหรับ 10100000200310310113030200221013111213110130332101 น่าจะเป็น 22 ใช่ไหม?
Erik the Outgolfer

2
การเพิ่มกรณีทดสอบที่ยุ่งยากเช่น12122111131อาจเป็นความคิดที่ดี
Emigna

คำตอบ:


5

Python 2 - 208 191 185 180 172 164 156 ไบต์

t=filter(bool,map(int,input()))
i=a=0
n=len(t)
while 0<n-1>i<11:
 if(t[i]>=3>t[i+1]):del t[i:i+2];i,n=0,n-2
 i+=1
for x in t[9::-1]:a+=a+x%2*(2-x-a)
print a

การพังทลายคือมันกำจัดอากาศและระเบิดถ้ามันอยู่บนสแต็กนับแล้ว

แก้ไข: ฉันเปลี่ยนไปใช้ Python 2 เพื่อบันทึกไบต์ แต่ตอนนี้อินพุตควรใส่วงเล็บปีกกาเช่น '3312123'

EDIT2: ฉันยังรู้สึกภูมิใจในตัวนับจำนวนสะสม

EDIT3: ขอบคุณสำหรับคำแนะนำทั้งหมดของคุณฉันไม่เคยคิดเลยว่าจะได้รับมันต่ำมาก


คำตอบแรกที่ดี! ฉันคิดกับ Python เหมือนกัน แต่ใช้เวลาไม่นาน คิดว่าคุณน่าจะเอาชนะแนวทางของฉันอยู่ดี
ElPedro

ขอบคุณสำหรับความคิดเห็นที่ดี :) ครั้งแรกที่ฉันเล่นกอล์ฟและฉันต้องบอกว่ามันสนุกมาก
Pâris Douady

ใช้t[:10][::-1]แทนreverse()การบันทึก 4 ไบต์และอาจใช้ Python 2 เพื่อบันทึกเครื่องหมายวงเล็บบนprint? มาถึง 5 ดวงช่วยชีวิตฉันได้มากขึ้น :)
ElPedro

ไม่มี Python2 สำหรับฉันเนื่องจากฉันจะต้องป้อนข้อมูล () เพื่อ str เพื่อให้ทำงานได้ฆ่าอีก 5 ดวง จับได้ดีเมื่อ [:: - 1]
Pâris Douady

btw ฉันไม่เห็นอะไรเลยในคำถามที่กล่าวว่าอินพุตสามารถ 'ถูกรวมอยู่ในเครื่องหมายคำพูดได้ เพียงแค่พูดว่า "การป้อนข้อมูลคือรายการของสิ่งต่าง ๆ " ทำงานใน Python 2 :)
ElPedro



3

Python 2, 150 146 bytes

v=[]
s=0
for c in input():
 v=v[:9]
 if'0'==c:1
 elif 3 in v[-1:]and c in'21':v=v[:-1]
 else:v+=[int(c)]
for x in v[::-1]:s+=s+x%2*(2-x-s)
print s

ขอบคุณPâris Douady สำหรับสูตรคะแนนและการบันทึก 4 ไบต์


คุณเอาสูตรของฉันมานับคะแนนหรือไม่? ไม่ว่าจะเป็นทางออกที่ดีคุณเอาชนะฉันและมันก็สะอาดกว่ามาก คุณสามารถบันทึกไบต์ด้วยการทำfor c in input()โดยตรง
Pâris Douady

2

Javascript, 267 264 249 วิญญาณเสียสละ

r='replace'
f=t=>{t=t[r](/0/g,'');while(/3[12]/.test(t.substring(0,10)))t=t[r](/3[12]/,'');
a=t.length-1;x=(t.substring(0,9)+(a>8?t[a]:'')).split('').reverse().join('');
c='c=0'+x[r](/1/g,'+1')[r](/2/g,';c*=2;c=c')[r](/3/g,'-1');eval(c);return c}

รุ่นที่แก้ไขแล้วเนื่องจากรุ่นก่อนหน้าไม่ถูกต้องสำหรับอินพุตที่มีขนาดใหญ่กว่า นำมาเพิ่มอีกเล็กน้อยโดยการstring.prototype.replace()โทรเข้าฟังก์ชันที่มีแถวลำดับ คำอธิบาย:

f=t=>{                                  Function declaration, input t
t=t.replace(/0/g,'');                   Remove air
while(/3[12]/.test(t.substring(0,10)))  Look for bombs; not double bombs, and only in the first 10 chars
    t=t.replace(/3[12]/,'');            Detonate bombs. If this makes a new bomb fall into the vase, or
                                        a double bomb is now a single bomb, it'll detonate that bomb too.
x=(t.substring(0,9)+                    Fill the vase, take the first 9 items
    (t.length>9?t[t.length-1]:''))      If we have more than 9 items, then add the last one
    .split('').reverse().join('');      Flip the instruction string.
c='c=0'+x.replace(/1/g,'+1')            Replace each item with the proper instruction to the ACC
         .replace(/2/g,';c*=2;c=c')
         .replace(/3/g,'-1');
eval(c);return c}                       Eval to get the value of ACC and return it.

f('11231');2ผลตอบแทน ลองออนไลน์


10100000200310310113030200221013111213110130332101 ไม่ส่งคืนผลลัพธ์ที่ดี :) คุณอยู่ใกล้ :) :)
Sygmei

@Sygmei ฉันรู้และฉันได้รับการแก้ไขอึออกจากมัน แต่ฉันไม่สามารถหาสาเหตุ คุณเห็นฉันในการแชทไหม
steenbergh

1

Haskell, 221 202 181 177 166 วิญญาณจำนวนไบต์

g(0:r)=r++[0]
g(3:x:r)|0<x,x<3=0:0:g r|1<3=3:g(x:r)
g(x:r)=x:g r
g r=r
v%(x:r)=g(init v++[x])%r
v%[]|v==g v=foldr([id,(+)1,(*)2,(-)1]!!)0v|1<3=g v%[]
(([0..9]>>[0])%)

ลองบน ideone ใช้รายการเป็นรายการจำนวนเต็ม

การใช้งาน:

*Prelude> (([0..9]>>[0])%) [1,2,1,2,2,1,1,1,1,3,1]
43

(แก้ไข: เก่า) คำอธิบาย:

g [] = []                             -- g simulates gravity in the vase
g ('0':r) = r ++ "0"                  -- the first 0 from the bottom is removed
g ('3':x:r) | elem x "12" = "00"++g r -- if a 1 or 2 is on a bomb, explode 
            | True = '3' : g(x:r)     -- else continue
g (x:r) = x : g r                     -- no air and no bomb, so check next item

c x = [id,(+)1,(*)2,(-)1]!!(read[x])  -- map 0, 1, 2, 3 to their score functions

f v w (x:r) =                         -- v is the current vase state, w the previous one
               init v++[x]            -- replace last vase element with input
             g(init v++[x])           -- simulate one gravity step
           f(g(init v++[x]))v r       -- repeat, w becomes v
f v w[] | v==w =                      -- if the input is empty and vase reached a fixpoint
                 foldr c 0 v          -- then compute score 
        | True = f (g v) v []         -- else simulate another gravity step


vase input = f "0000000000" "" input  -- call f with empty vase, previous vase state and
                                      -- the input as string of numbers

ทำได้ดีมาก :)! สามตัวสุดท้ายคืออะไร?
Sygmei

@Sygmei เป็นสองสายf "0000000000" ""คุณไม่ต้องการเว้นวรรคระหว่างพวกเขา ฉันเพิ่มคำอธิบายลงในรหัส
Laikoni

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