นับรูปแบบเกมแห่งชีวิตทั่วไป


21

ภารกิจที่นี่คือการอ่านจาก.rleไฟล์Golly หรือข้อความธรรมดา (ตัวเลือกของคุณ) ที่มีชื่อไฟล์ให้ (บน STDIN หรือเป็นอาร์กิวเมนต์บรรทัดคำสั่ง) และระบุและนับรูปแบบทั่วไปในตารางที่เข้ารหัสในนั้น

หรือคุณอาจเลือกที่จะมีเนื้อหาของไฟล์ที่ให้โดยตรงผ่าน STDIN แทน

โปรแกรมของคุณควรจะสามารถระบุและเห็นความแตกต่างอย่างน้อยสิบห้าร่วมกับสิ่งมีชีวิตยังคงเข้มงวดและห้า oscillators ที่พบมากที่สุดรวมทั้งร่อน

ขั้นตอนทั้งหมดของออสซิลเลเตอร์เหล่านี้ควรได้รับการยอมรับเช่นเดียวกับขั้นตอนทั้งสี่ของเครื่องร่อน

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

รูปแบบที่เป็นส่วนหนึ่งของรูปแบบอื่น ๆ ที่นับไม่ควรนับ (ตัวอย่างเช่น 8-cell phase ของสัญญาณไม่ควรนับเป็นสองช่วงตึกและไม่ควรนับ tie-ship เป็นสองเรือรบ)

คุณอาจสมมติว่าอินพุตมีความเสถียรแล้วและไม่มีรูปแบบใดที่ไม่อยู่ในชุดที่กำหนด คุณอาจสมมติว่ากริดอินพุตจะพอดีภายในกล่อง 1024x1024

นี่คือดังนั้นโปรแกรมที่สั้นที่สุดชนะ

คำอธิบายรูปแบบไฟล์ RLE

ไฟล์ RLE มีกริดไลฟ์แบบเข้ารหัสความยาววิ่ง บรรทัดทั้งหมดที่ขึ้นต้นด้วย#ความคิดเห็นและควรละเว้น

x=<width>,y=<height>,rule=<rule>ครั้งแรกที่สายไม่ว่างเปล่าที่ไม่แสดงความคิดเห็นเป็นของแบบฟอร์ม B3/S23สำหรับจุดประสงค์ของงานนี้กฎจะเป็น มันอาจมีช่องว่างที่ควรถอดก่อนประมวลผลบรรทัดนี้ (แน่นอนว่าไม่จำเป็นต้องประมวลผลบรรทัดนี้เลย)

บรรทัดที่ไม่ใช่ความคิดเห็นหลังจากบรรทัดแรกควรถูกใช้เป็นสตริงเดี่ยว นี้ควรมีเพียงตัวเลขทศนิยม, ตัวละคร$, bและoและแบ่งบรรทัดและจะไม่จบลงด้วยหลัก การขึ้นบรรทัดใหม่นั้นจะถูกเพิกเฉย แต่คุณอาจคิดว่าการขึ้นบรรทัดใหม่นั้นจะไม่รบกวนสตริงของตัวเลข

!นี้อาจถูกยกเลิกโดยเป็นหนึ่งเดียว

bหมายถึงเซลล์ที่ตายแล้วoหมายถึงเซลล์ที่มีชีวิตและ$แสดงถึงจุดสิ้นสุดของแถว เลขทศนิยมใด ๆ บ่งชี้ว่าสัญลักษณ์ต่อไปนี้จะต้องได้รับการปฏิบัติเหมือนเป็นการทำซ้ำหลายครั้ง

การเข้ารหัสรูปแบบธรรมดา

ตัวเลือกอื่นคือการอ่านรูปแบบในรูปแบบข้อความธรรมดาอื่นที่อธิบายไว้ที่นี่ ในการเข้ารหัสนี้เซลล์ที่ปิดจะแสดงด้วยเครื่องหมายยัติภังค์และในเซลล์จะถูกแสดงด้วยตัวพิมพ์ใหญ่ Os โดยมีบรรทัดใหม่คั่นแถว

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

บรรทัดที่ขึ้นต้นด้วย!คือความคิดเห็นและควรละเว้น

บางกรณีทดสอบ

RLE:

#This is a comment
x = 35, y = 16, rule = B3/S23
bo$2o$obo5$22bo$22bo$22bo2$18b3o3b3o2$22bo$22bo10b2o$22bo10b2o!

ข้อความธรรมดา:

!This is a comment
-O---------------------------------
OO---------------------------------
O-O--------------------------------
-----------------------------------
-----------------------------------
-----------------------------------
-----------------------------------
----------------------O------------
----------------------O------------
----------------------O------------
-----------------------------------
------------------OOO---OOO--------
-----------------------------------
----------------------O------------
----------------------O----------OO
----------------------O----------OO

ผล:

Glider 1
Blinker 4
Block 1

RLE:

x = 27, y = 15, rule = B3/S23
5b2o$5b2o9$11bo$o9bobo$o9bobo$o10bo12b3o!
#Here's a comment at the end

ข้อความธรรมดา:

-----OO--------------------
-----OO--------------------
---------------------------
---------------------------
---------------------------
---------------------------
---------------------------
---------------------------
---------------------------
---------------------------
-----------O---------------
O---------O-O--------------
O---------O-O--------------
O----------O------------OOO
!Here's a comment at the end

ผล:

Block 1
Blinker 2
Beehive 1

RLE:

#You may have multiple comments
#As shown here
x = 13, y = 11, rule = B3/S23
2o$2o2$12bo$12bo$12bo$2b2o$2b2o4b2o$7bo2bo$7bobo$8bo!

ข้อความธรรมดา:

!You may have multiple comments
!As shown here
OO-----------
OO-----------
-------------
------------O
------------O
------------O
--OO---------
--OO----OO---
-------O--O--
-------O-O---
--------O----

ผล:

Block 2
Blinker 1
Loaf 1

RLE:

# Pentadecathlon
# Discovered by John Conway
# www.conwaylife.com/wiki/index.php?title=Pentadecathlon
x = 10, y = 3, rule = B3/S23
2bo4bo2b$2ob4ob2o$2bo4bo!

ข้อความธรรมดา:

! Pentadecathlon
! Discovered by John Conway
! www.conwaylife.com/wiki/index.php?title=Pentadecathlon
--O----O--
OO-OOOO-OO
--O----O--

ผล:

Pentadecathlon 1

โบนัส

หากคุณสนับสนุนทั้งรูปแบบการป้อนข้อมูล (ใช้นามสกุลไฟล์ [ .rleสำหรับไฟล์ rle และ.cellsสำหรับธรรมดา - วิธีการอ่านส่วนขยายอื่น ๆ นั้นไม่ได้กำหนดไว้] หรือการตั้งค่าสถานะบรรทัดคำสั่งเพื่อแยกแยะระหว่างพวกเขา) คุณอาจลบ 5% จากคะแนนของคุณ


แล้วOOO.OO\n....OO
Akangka

@ChristianIrwan ดีนั่นไม่ใช่รูปแบบที่เสถียรดังนั้นคุณจะไม่ได้รับมันเป็นอินพุต
SuperJedi224

คำตอบ:


13

Haskell, 2417 ไบต์

สิ่งนี้ใช้เวลาสักครู่และยังมีข้อบกพร่องอยู่เล็กน้อย แต่ฉันมีลูกเล่นหลายอย่างที่ใช้งานได้ดังนั้นมันจึงคุ้มค่า

หมายเหตุ:

  • ยอมรับเฉพาะรูปแบบข้อความธรรมดาที่ส่งผ่านไปยัง STDIN
  • ใช้เวลาประมาณ O (n ^ 20)
  • ฉันสันนิษฐานว่าจำนวนตัวอักษรในบรรทัดที่ไม่ใช่ความคิดเห็นเป็นค่าคงที่ (ภายในอินพุตที่ระบุ) เนื่องจากเป็นวิธีในตัวอย่าง
  • เคล็ดลับ Craziest เป็นวิธีที่รูปแบบจะแตกแพ็คแยกองค์ประกอบที่ตำแหน่ง (หมายเลขคอลัมน์) โมดูโล (ความยาวของผลลัพธ์) เพื่อสร้างอาร์เรย์

มันรวมความคิดหลัก ๆ สองสามข้อ:

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

นี่คือรหัส:

r=[1..20]
a!0=a!!0
a!x=tail a!(x-1)
u[_,x,y,l]=[[odd$div l$2^i|i<-[0..y],mod i x==j]|j<-[0..x-1]]
main=interact(\s->let q=[map(=='O')l|l<-lines s,l!0/='!']in let g=[i|i<-[[[0,3,11,3339,0,4,11,924,0,4,11,3219,0,3,11,1638,1,4,15,19026,1,4,15,9636,2,3,11,1386,2,4,11,1686,3,7,48,143505703994502,3,7,48,26700311308320,3,7,48,213590917399170,3,7,48,8970354435120,4,2,3,15,5,3,8,171,5,3,8,174,5,3,8,426,5,3,8,234,6,4,15,36371,6,4,15,12972,6,4,15,51313,6,4,15,13644,6,4,15,50259,6,4,15,12776,6,4,15,51747,6,4,15,6028,7,4,15,26962,7,4,15,9622,7,4,15,19094,7,4,15,27044,8,5,24,9054370,8,5,24,2271880,9,4,15,51794,9,4,15,13732,9,4,15,19027,9,4,15,9644,10,4,19,305490,10,5,19,206412,10,5,19,411942,10,4,19,154020,11,3,8,427,11,3,8,238,12,6,35,52217012547,12,6,35,3306785328,13,3,8,170,14,3,8,428,14,3,8,458,14,3,8,107,14,3,8,167,14,3,8,482,14,3,8,302,14,3,8,143,14,3,8,233,14,3,8,241,14,3,8,157,14,3,8,286,14,3,8,370,14,3,8,181,14,3,8,115,14,3,8,346,14,3,8,412,15,4,15,51219,15,4,15,12684,15,4,15,52275,15,4,15,13260,16,1,2,7,16,3,2,7,17,3,29,313075026,17,10,29,139324548,17,3,23,16252911,17,8,23,16760319,17,5,49,152335562622276,17,10,49,277354493774076,17,7,69,75835515713922895368,17,10,69,138634868908666122360,17,9,89,135722011765098439128942648,17,10,89,58184575467336340020006960,17,5,59,160968502306438596,17,12,59,145347113669124612,17,5,59,524156984170595886,17,12,59,434193401052698118,17,5,69,164495599269019571652,17,14,69,222245969722444385292,17,5,69,517140479305239282702,17,14,69,222262922122170485772,17,3,47,83020951028178,17,16,47,39740928107556,17,3,35,62664969879,17,12,35,40432499049,17,3,41,1581499314234,17,14,41,1293532058322,17,3,41,4349006881983,17,14,41,3376910168355,17,3,47,92426891685930,17,16,47,83780021865522,17,3,47,79346167206930,17,16,47,11342241794640,18,13,168,166245817041425752669390138490014048702557312780060,18,15,224,1711376967527965679922107419525530922835414769336784993839766570000,18,13,168,141409121010242927634239017227763246261766273041932,19,2,7,126,19,4,7,231,19,4,7,126,19,2,7,189,19,4,15,24966,19,4,15,18834,19,4,15,10644,19,4,15,26646]!p|p<-[h..h+3]]|h<-[0,4..424]],j<-[[[q!y!x|x<-[a..a+c]]|y<-[b..b+d]]|c<-r,d<-r,a<-[0..(length$q!0)-c-1],b<-[0..length q-d-1]],u i==j]in show[(words"aircraftcarrier barge beehive biloaf1 block boat eater1 loaf longbarge longboat mango ship shiptie tub glider beacon blinker pentadecathlon pulsar toad"!(e!0),sum[1|f<-g,e!0==f!0])|e<-g])

ต่อไปนี้เป็นรหัส Mathematica ที่ใช้ในการแพ็คอาร์เรย์ 0,1 ลงในรูปแบบซึ่งจะแตกในภายหลังโดยโปรแกรม Haskell:

rotate[m_]:=Transpose[Map[Reverse,m]]
findInversePermutation[m_]:=Block[{y=Length[First[m]], x=Length[m]}, InversePermutation[FindPermutation[Flatten[m], Flatten[Table[Table[Flatten[m][[i+1]], {i, Select[Range[0, x * y - 1], Mod[#, x]==j&]}], {j, 0, x - 1}]]]]]
enumShape[m_]:=Partition[Range[1, Length[Flatten[m]]], Length[m[[1]]]]
pack[m_]:={Length[rotate[rotate[m]]], Length[Flatten[rotate[rotate[m]]]], FromDigits[Permute[Flatten[rotate[rotate[m]]], findInversePermutation[enumShape[rotate[rotate[m]]]]], 2]}

นี่เป็นโค้ดที่สมบูรณ์ยิ่งขึ้น

range = [1..16]          -- all of the patterns fall within this range

list ! 0        = list !! 0           -- this is a simple generic (!!)
list ! position = (tail list) ! (position - 1)

unpack [_, unpackedLength, unpackedSize, packed] = [ [odd $ div packed (2^i) | i <- [0..unpackedSize], (mod i unpackedLength) == j] | j <- [0..unpackedLength - 1]]

main=interact doer

doer input = show $ tallyByFirst (words nameString) foundPatterns -- this counts equalities between the list of patterns and the submatrices of the input
  where
    parsed = parse input -- this selects the non-comment lines and converts to an array of Bool's
    foundPatterns = countOccurrences partitioned subArrays
    subArrays     = allSubArrays parsed
    partitioned   = modPartition compressed 428 4 -- this partitions the compressed patterns into the form [name number, x length, x length * y length, packed integer]

countOccurrences patterns subArrays = [pattern | pattern <- patterns, subArray <- allSubArrays q, unpack pattern == subArray]

subArray m offsetX subSizeX offsetY subSizeY = [[m ! y ! x | x <- [offsetX..offsetX + subSizeX]] | y <- [offsetY..offsetY + subSizeY]]

allSubArrays m = [subArray m offsetX subSizeX offsetY subSizeY | subSizeX <- range, subSizeY <- range, offsetX <- [0.. (length $ head m) - subSizeX - 1], offsetY <- [0..(length m) - subSizeY - 1]]

tallyByFirst names list = [ (names ! (a ! 0), sum [1 | a <- list, (head a) == (head b)]) | b <- list]

parse string = [map (=='O') line | line <- lines string, head line /= '!']

modPartition list chunksize = [ [list ! position | position <- [offset..offset + chunksize - 1]] | offset <- [0, chunksize..(length list) - chunksize]]

ยินดีต้อนรับสู่ PPCG! ฉันยังไม่ได้ลอง แต่ก็ดูน่าประทับใจ +1!
ปาเก็ตตี้

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