Hopping Bunny ของ Google


16

เมื่อวันที่ 4 ธันวาคม 2017 ของ Google Doodle เป็นเกมการเขียนโปรแกรมแบบกราฟิกที่มีกระต่าย ระดับต่อมาได้อย่างไม่น่ารำคาญและพวกเขาดูเหมือนจะเป็นผู้สมัครที่ดีสำหรับที่ท้าทาย

รายละเอียด

เกม

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

รหัสของคุณ

  • วัตถุประสงค์: ให้คณะกรรมการค้นหาวิธีแก้ปัญหาที่สั้นที่สุดหนึ่งรายการหรือมากกว่า
  • การป้อนข้อมูลเป็นรายการของสแควร์ที่ตั้งคณะกรรมการ (แยกความแตกต่างสี่เหลี่ยมที่ทำเครื่องหมายและไม่ได้ทำเครื่องหมาย) และเอาท์พุทเป็นรายการของการเคลื่อนไหว รูปแบบอินพุตและเอาต์พุตไม่สำคัญเลยตราบใดที่รูปแบบที่มนุษย์สามารถอ่านและเข้าใจได้
  • เกณฑ์การชนะ:ผลรวมของจำนวนการเคลื่อนไหวของการแก้ปัญหาที่สั้นที่สุดที่พบภายในหนึ่งนาทีสำหรับแต่ละกระดาน หากโปรแกรมของคุณไม่พบวิธีแก้ปัญหาสำหรับบอร์ดใด ๆ คะแนนของคุณสำหรับบอร์ดนั้นคือ (5 * จำนวนสี่เหลี่ยม)
  • โปรดอย่าแก้ไขปัญหาฮาร์ดโค้ดในลักษณะใด ๆ รหัสของคุณควรจะนำบอร์ดใด ๆ เป็นอินพุตไม่ใช่แค่ตัวอย่างที่ให้ไว้ด้านล่าง

ตัวอย่าง

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

Sคือจัตุรัสเริ่มต้นของกระต่าย (หันหน้าไปทางทิศตะวันออก) #เป็นสี่เหลี่ยมที่ไม่มีเครื่องหมายและOเป็นสี่เหลี่ยมจัตุรัส สำหรับการเคลื่อนไหวเครื่องหมายของฉันคือF= กระโดดไปข้างหน้าL= เลี้ยวซ้ายR= เลี้ยวขวาและLOOP(<num>){<moves>}หมายถึงการวนซ้ำที่วนซ้ำ<num>และทำ<moves>ในแต่ละครั้ง หากการวนซ้ำสามารถเรียกใช้จำนวนครั้งเกินจำนวนขั้นต่ำบางอย่าง<num>อาจถูกละเว้น (เช่นอินฟินิตี้ทำงาน)

ระดับ 1:

S##

FF

ระดับ 2:

S##
  #
  #

LOOP (2) {} FFR

ระดับ 3:

S##
# #
###

LOOP {} FFR

ระดับ 4:

###
# #
##S##
  # #
  ###

LOOP {F LOOP (7) {FL}} (ค้นพบโดย DJMcMayhem)

ระดับ 5:

#####
# # #
##S##
# # #
#####

LOOP (18) {LOOP (10) {FR} L}
แหล่งที่มา: Reddit

ระดับ 6:

 ###
#OOO#
#OSO#
#OOO#
 ###

LOOP {LOOP (3) {F} L}

บอร์ดขนาดใหญ่: (ไม่ทราบวิธีแก้ปัญหาที่สั้นที่สุดในปัจจุบัน)

12x12:

S###########
############
############
############
############
############
############
############
############
############
############
############

ระดับ 5 แต่ใหญ่กว่า:

#############
# # # # # # #
#############
# # # # # # #
#############
# # # # # # #
######S######
# # # # # # #
#############
# # # # # # #
#############
# # # # # # #
#############

บอร์ดที่มีโพรงเพิ่มเติม:

S##########
###########
## ## ## ##
###########
###########
## ## ## ##
###########
###########
## ## ## ##
###########
###########

และ

S#########
##########
##  ##  ##
##  ##  ##
##########
##########
##  ##  ##
##  ##  ##
##########
##########

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

#######
# ##  #
#######
###S###
# ##  #
# ##  #
#######

และ

#########
# ##  ###
###S  ###
# #######
###    ##
#####   #
####  ###
#########
#########

ที่เกี่ยวข้อง
Mr. Xcoder

"หาทางแก้ปัญหาที่สั้นที่สุดอย่างน้อยหนึ่งวิธี" ฉันคิดว่าปัญหาการหยุดชะงักนี้ห้ามไม่ให้เกิดขึ้น
Leaky Nun

@Leaky Nun สิ่งนี้ไม่เกี่ยวข้องกับปัญหาการหยุดทำงาน นี่คือการค้นหากราฟ
WhatToDo

แต่อนุญาตให้วนซ้ำ ...
แม่ชีที่ไม่แน่นอน

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

คำตอบ:


12

Python 3, 67 โทเค็น

import sys
import time

class Bunny():
    def __init__(self):
        self.direction = [0, 1]
        self.coords = [-1, -1]

    def setCoords(self, x, y):
        self.coords = [x, y]

    def rotate(self, dir):
        directions = [[1, 0], [0, 1], [-1, 0], [0, -1]]
        if dir == 'L':
            self.direction = directions[(directions.index(self.direction) + 1) % 4]
        if dir == 'R':
            self.direction = directions[(directions.index(self.direction) - 1) % 4]

    def hop(self):
        self.coords = self.nextTile()

    # Returns where the bunny is about to jump to
    def nextTile(self):
        return [self.coords[0] + self.direction[0], self.coords[1] + self.direction[1]]

class BoardState():
    def __init__(self, map):
        self.unvisited = 0
        self.map = []

        self.bunny = Bunny()
        self.hopsLeft = 0

        for x, row in enumerate(map):
            newRow = []
            for y, char in enumerate(row):
                if char == '#':
                    newRow.append(1)
                    self.unvisited += 1

                elif char == 'S':
                    newRow.append(2)

                    if -1 in self.bunny.coords:
                        self.bunny.setCoords(x, y)
                    else:
                        print("Multiple starting points found", file=sys.stderr)
                        sys.exit(1)

                elif char == ' ':
                    newRow.append(0)

                elif char == 'O':
                    newRow.append(2)

                else:
                    print("Invalid char in input", file=sys.stderr)
                    sys.exit(1)

            self.map.append(newRow)

        if -1 in self.bunny.coords:
            print("No starting point defined", file=sys.stderr)
            sys.exit(1)

    def finished(self):
        return self.unvisited == 0

    def validCoords(self, x, y):
        return -1 < x < len(self.map) and -1 < y < len(self.map[0])

    def runCom(self, com):
        if self.finished():
            return

        if self.hopsLeft < self.unvisited:
            return

        if com == 'F':
            x, y = self.bunny.nextTile()
            if self.validCoords(x, y) and self.map[x][y] != 0:
                self.bunny.hop()
                self.hopsLeft -= 1

                if (self.map[x][y] == 1):
                    self.unvisited -= 1
                self.map[x][y] = 2

        else:
            self.bunny.rotate(com)

class loop():
    def __init__(self, loops, commands):
        self.loops = loops
        self.commands = [*commands]

    def __str__(self):
        return "loop({}, {})".format(self.loops, list(self.commands))

    def __repr__(self):
        return str(self)


def rejectRedundantCode(code):
    if isSnippetRedundant(code):
        return False

    if type(code[-1]) is str:
        if code[-1] in "LR":
            return False
    else:
        if len(code[-1].commands) == 1:
            print(code)
            if code[-1].commands[-1] in "LR":
                return False

    return True


def isSnippetRedundant(code):
    joined = "".join(str(com) for com in code)

    if any(redCode in joined for redCode in ["FFF", "RL", "LR", "RRR", "LLL"]):
        return True

    for com in code:
        if type(com) is not str:
            if len(com.commands) == 1:
                if com.loops == 2:
                    return True

                if type(com.commands[0]) is not str:
                    return True

                if com.commands[0] in "LR":
                    return True

            if len(com.commands) > 1 and len(set(com.commands)) == 1:
                return True

            if isSnippetRedundant(com.commands):
                return True

    for i in range(len(code)):
        if type(code[i]) is not str and len(code[i].commands) == 1:
            if i > 0 and code[i].commands[0] == code[i-1]:
                return True
            if i < len(code) - 1 and code[i].commands[0] == code[i+1]:
                return True

        if type(code[i]) is not str:
            if i > 0 and type(code[i-1]) is not str and code[i].commands == code[i-1].commands:
                return True
            if i < len(code) - 1 and type(code[i+1]) is not str and code[i].commands == code[i+1].commands:
                return True

            if len(code[i].commands) > 3 and all(type(com) is str for com in code[i].commands):
                return True

    return False

def flatten(code):
    flat = ""
    for com in code:
        if type(com) is str:
            flat += com
        else:
            flat += flatten(com.commands) * com.loops

    return flat

def newGen(n, topLevel = True):
    maxLoops = 9
    minLoops = 2
    if n < 1:
        yield []

    if n == 1:
        yield from [["F"], ["L"], ["R"]]

    elif n == 2:
        yield from [["F", "F"], ["F", "L"], ["F", "R"], ["L", "F"], ["R", "F"]]

    elif n == 3:
        for innerCode in newGen(n - 1, False):
            for loops in range(minLoops, maxLoops):
                if len(innerCode) != 1 and 0 < innerCode.count('F') < 2:
                    yield [loop(loops, innerCode)]

        for com in "FLR":
            for suffix in newGen(n - 2, False):
                for loops in range(minLoops, maxLoops):
                    if com not in suffix:
                        yield [loop(loops, [com])] + suffix

    else:
        for innerCode in newGen(n - 1, False):
            if topLevel:
                yield [loop(17, innerCode)]
            else:
                for loops in range(minLoops, maxLoops):
                    if len(innerCode) > 1:
                        yield [loop(loops, innerCode)]

        for com in "FLR":
            for innerCode in newGen(n - 2, False):
                for loops in range(minLoops, maxLoops):
                    yield [loop(loops, innerCode)] + [com]
                    yield [com] + [loop(loops, innerCode)]

def codeLen(code):
    l = 0
    for com in code:
        l += 1
        if type(com) is not str:
            l += codeLen(com.commands)

    return l


def test(code, board):
    state = BoardState(board)
    state.hopsLeft = flatten(code).count('F')

    for com in code:
        state.runCom(com)


    return state.finished()

def testAll():
    score = 0
    for i, board in enumerate(boards):
        print("\n\nTesting board {}:".format(i + 1))
        #print('\n'.join(board),'\n')
        start = time.time()

        found = False
        tested = set()

        for maxLen in range(1, 12):
            lenCount = 0
            for code in filter(rejectRedundantCode, newGen(maxLen)):
                testCode = flatten(code)
                if testCode in tested:
                    continue

                tested.add(testCode)

                lenCount += 1
                if test(testCode, board):
                    found = True

                    stop = time.time()
                    print("{} token solution found in {} seconds".format(maxLen, stop - start))
                    print(code)
                    score += maxLen
                    break

            if found:
                break

    print("Final Score: {}".format(score))

def testOne(board):
    start = time.time()
    found = False
    tested = set()
    dupes = 0

    for maxLen in range(1, 12):
        lenCount = 0
        for code in filter(rejectRedundantCode, newGen(maxLen)):
            testCode = flatten(code)
            if testCode in tested:
                dupes += 1
                continue

            tested.add(testCode)

            lenCount += 1
            if test(testCode, board):
                found = True
                print(code)
                print("{} dupes found".format(dupes))
                break

        if found:
            break

        print("Length:\t{}\t\tCombinations:\t{}".format(maxLen, lenCount))

    stop = time.time()
    print(stop - start)

#testAll()
testOne(input().split('\n'))

โปรแกรมนี้จะทดสอบคณะกรรมการการป้อนข้อมูลเดียว แต่ผมพบว่าคนขับรถทดสอบนี้มีประโยชน์มากขึ้น มันจะทดสอบทุกบอร์ดในเวลาเดียวกันและพิมพ์ระยะเวลาที่ใช้ในการค้นหาวิธีแก้ปัญหานั้น เมื่อฉันเรียกใช้รหัสนั้นบนเครื่องของฉัน (Intel i7-7700K quad core CPU @ 4.20 GHz, 16.0 GB RAM) ฉันจะได้ผลลัพธ์ต่อไปนี้:

Testing board 1:
2 token solution found in 0.0 seconds
['F', 'F']


Testing board 2:
4 token solution found in 0.0025103092193603516 seconds
[loop(17, [loop(3, ['F']), 'R'])]


Testing board 3:
4 token solution found in 0.0010025501251220703 seconds
[loop(17, [loop(3, ['F']), 'L'])]


Testing board 4:
5 token solution found in 0.012532949447631836 seconds
[loop(17, ['F', loop(7, ['F', 'L'])])]


Testing board 5:
5 token solution found in 0.011022329330444336 seconds
[loop(17, ['F', loop(5, ['F', 'L'])])]


Testing board 6:
4 token solution found in 0.0015044212341308594 seconds
[loop(17, [loop(3, ['F']), 'L'])]


Testing board 7:
8 token solution found in 29.32585096359253 seconds
[loop(17, [loop(4, [loop(5, [loop(6, ['F']), 'L']), 'L']), 'F'])]


Testing board 8:
8 token solution found in 17.202533721923828 seconds
[loop(17, ['F', loop(7, [loop(5, [loop(4, ['F']), 'L']), 'F'])])]


Testing board 9:
6 token solution found in 0.10585856437683105 seconds
[loop(17, [loop(7, [loop(4, ['F']), 'L']), 'F'])]


Testing board 10:
6 token solution found in 0.12129759788513184 seconds
[loop(17, [loop(7, [loop(5, ['F']), 'L']), 'F'])]


Testing board 11:
7 token solution found in 4.331984758377075 seconds
[loop(17, [loop(8, ['F', loop(5, ['F', 'L'])]), 'L'])]


Testing board 12:
8 token solution found in 58.620323181152344 seconds
[loop(17, [loop(3, ['F', loop(4, [loop(3, ['F']), 'R'])]), 'L'])]

Final Score: 67

การทดสอบครั้งสุดท้ายนี้แทบไม่ส่งเสียงดังภายใต้ข้อ จำกัด นาที

พื้นหลัง

นี่เป็นหนึ่งในความท้าทายที่สนุกที่สุดที่ฉันเคยตอบ! ฉันมีรูปแบบการระเบิดและค้นหาฮิวริสติกเพื่อลดสิ่งต่างๆ

โดยทั่วไปแล้วที่นี่ใน PPCG ฉันมักจะตอบคำถามที่ค่อนข้างง่าย ฉันชอบแท็กมากเป็นพิเศษเพราะโดยทั่วไปแล้วมันค่อนข้างจะเหมาะสำหรับภาษาของฉัน วันหนึ่งประมาณสองสัปดาห์ที่ผ่านมาฉันกำลังดูตราของฉันและฉันรู้ว่าฉันไม่เคยได้รับตราการฟื้นฟู ดังนั้นฉันจึงมองผ่านคนที่ไม่ได้รับคำตอบแท็บเพื่อดูว่ามีอะไรสะดุดตาหรือไม่และฉันพบคำถามนี้ ฉันตัดสินใจว่าฉันจะตอบมันไม่ว่าจะมีราคาเท่าใด ท้ายที่สุดมันก็ยากกว่าที่ฉันคิด แต่ท้ายที่สุดฉันก็ได้รับคำตอบที่โหดร้ายที่ฉันสามารถพูดได้ว่าฉันภูมิใจ แต่ความท้าทายนี้ไม่ได้มาตรฐานสำหรับฉันเพราะฉันมักจะไม่ใช้เวลามากกว่าหนึ่งชั่วโมงหรือมากกว่านั้นในคำตอบเดียว คำตอบนี้ใช้เวลากว่า 2 สัปดาห์และอย่างน้อย 10+ งานเพื่อไปถึงขั้นตอนนี้แม้ว่าฉันจะไม่ได้ติดตามอย่างระมัดระวัง

การทำซ้ำครั้งแรกคือวิธีการแก้ปัญหากำลังดุร้ายบริสุทธิ์ ฉันใช้รหัสต่อไปนี้เพื่อสร้างตัวอย่างทั้งหมดยาวไม่เกินN :

def generateCodeLenN(n, maxLoopComs, maxLoops, allowRedundant = False):
    if n < 1:
        return []

    if n == 1:
        return [["F"], ["L"], ["R"]]

    results = []

    if 1:
        for com in "FLR":
            for suffix in generateCodeLenN(n - 1, maxLoopComs, maxLoops, allowRedundant):
                if allowRedundant or not isSnippetRedundant([com] + suffix):
                    results.append([com] + suffix)

    for loopCount in range(2, maxLoopComs):
        for loopComs in range(1, n):
            for innerCode in generateCodeLenN(loopComs, maxLoopComs, maxLoops - 1, allowRedundant):
                if not allowRedundant and isSnippetRedundant([loop(loopCount, innerCode)]):
                    continue

                for suffix in generateCodeLenN(n - loopComs - 1, maxLoopComs, maxLoops - 1, allowRedundant):
                    if not allowRedundant and isSnippetRedundant([loop(loopCount, innerCode)] + suffix):
                        continue

                    results.append([loop(loopCount, innerCode)] + suffix)

                if loopComs == n - 1:
                    results.append([loop(loopCount, innerCode)])

    return results

ณ จุดนี้ฉันมั่นใจว่าการทดสอบคำตอบเดียวที่เป็นไปได้ทั้งหมดจะช้าเกินไปดังนั้นฉันจึงใช้isSnippetRedundantการกรองตัวอย่างที่สามารถเขียนด้วยตัวอย่างข้อมูลที่สั้นกว่า ตัวอย่างเช่นฉันจะปฏิเสธที่จะให้ตัวอย่าง["F", "F", "F"]เพราะผลเหมือนกันที่แน่นอนสามารถทำได้ด้วย[Loop(3, ["F"])ดังนั้นหากเราไปถึงจุดที่เราทดสอบความยาว 3 ตัวอย่างเรารู้ว่าไม่มีความยาว 3 ตัวอย่างสามารถแก้บอร์ดปัจจุบัน สิ่งนี้ใช้ความจำที่ดีมากมาย แต่ท้ายที่สุดก็คือwaaaayช้าเกินไป. Testcase 12 ใช้เวลาเพียง 3,000 วินาทีโดยใช้วิธีการนี้ เห็นได้ชัดว่าช้าเกินไปอย่างเห็นได้ชัด แต่ด้วยการใช้ข้อมูลนี้และวงจรคอมพิวเตอร์จำนวนมากเพื่อแก้ไขปัญหาสั้น ๆ ให้กับบอร์ดทุกตัวฉันสามารถหารูปแบบใหม่ได้ ฉันสังเกตเห็นว่าเกือบทุกวิธีแก้ปัญหาที่พบโดยทั่วไปจะมีลักษณะเหมือนดังต่อไปนี้:

[<com> loop(n, []) <com>]

ซ้อนกันหลายชั้นลึกโดยมี coms เดียวในแต่ละด้านเป็นตัวเลือก ซึ่งหมายความว่าวิธีแก้ปัญหาเช่น:

["F", "F", "R", "F", "F", "L", "R", "F", "L"]

จะไม่ปรากฏขึ้น ในความเป็นจริงไม่เคยมีลำดับของโทเค็นที่ไม่วนซ้ำมากกว่า 3 ครั้ง วิธีหนึ่งในการใช้สิ่งนี้คือการกรองสิ่งเหล่านี้ทั้งหมดและไม่สนใจที่จะทดสอบ แต่การสร้างพวกเขายังคงใช้เวลาไม่น้อยและการกรองตัวอย่างข้อมูลนับล้าน ๆ แบบนี้จะช่วยลดเวลา แต่ฉันเขียนโค้ดตัวสร้างซ้ำอย่างมากเพื่อสร้างตัวอย่างเท่านั้นตามรูปแบบนี้ ในรหัสเทียมตัวสร้างใหม่ตามรูปแบบทั่วไปนี้:

def codeGen(n):
    if n == 1:
        yield each [<com>]

    if n == 2:
        yield each [<com>, <com>]

    if n == 3:
        yield each [loop(n, <com length 2>]
        yield each [loop(n, <com>), <com>]

    else:
        yield each [loop(n, <com length n-1>)]
        yield each [loop(n, <com length n-2>), <com>]
        yield each [<com>, loop(n, <com length n-2>)]

        # Removed later
        # yield each [<com>, loop(n, <com length n-3>), <com>]
        # yield each [<com>, <com>, loop(n, <com length n-3>)]
        # yield each [loop(n, <com length n-3>), <com>, <com>]

กรณีนี้ทำให้การทดสอบนานที่สุดลดลงเหลือ 140 วินาทีซึ่งเป็นการปรับปรุงที่ไร้สาระ แต่จากที่นี่ยังมีบางสิ่งที่ฉันต้องปรับปรุง ฉันเริ่มกรองโค้ดที่ซ้ำซ้อน / ไร้ค่ายิ่งขึ้นและทำการตรวจสอบเพื่อดูว่ามีการทดสอบรหัสมาก่อนหรือไม่ สิ่งนี้ตัดมันลงไปอีก แต่ก็ยังไม่เพียงพอ ในท้ายที่สุดชิ้นสุดท้ายที่หายไปคือเคาน์เตอร์วน ผ่านอัลกอริธึมขั้นสูงของฉัน (อ่าน: การพิจารณาคดีแบบสุ่มและข้อผิดพลาด ) ฉันพบว่าช่วงที่เหมาะสมที่สุดในการอนุญาตให้ลูปทำงานคือ [3-8] แต่มีการปรับปรุงอย่างมากในนั้น: ถ้าเรารู้ว่า[loop(8, [loop(8, ['F', loop(5, ['F', 'L'])]), 'L'])]ไม่สามารถแก้ปัญหาบอร์ดของเราได้[loop(3, [loop(8, ['F', loop(5, ['F', 'L'])]), 'L'])]หรือนับวงใด ๆ จาก 3-7 สามารถแก้ปัญหาได้ ดังนั้นแทนที่จะวนซ้ำวนวนทุกขนาดตั้งแต่ 3-8 เราตั้งค่าการนับลูปบนลูปภายนอกเป็นสูงสุด นี่จะเป็นการลดพื้นที่การค้นหาลงด้วยปัจจัยmaxLoop - minLoopหรือ 6 ในกรณีนี้

สิ่งนี้ช่วยได้มาก แต่จบลงด้วยคะแนนที่สูงขึ้น วิธีการแก้ปัญหาบางอย่างที่ฉันพบก่อนหน้านี้โดยกำลังดุร้ายต้องใช้หมายเลขลูปที่ใหญ่กว่าเพื่อเรียกใช้ (ตัวอย่างเช่นบอร์ด 4 และ 6) ดังนั้นแทนที่จะตั้งค่าการวนรอบนอกเป็น 8 เราตั้งค่าการวนรอบนอกเป็น 17 ตัวเลขมหัศจรรย์คำนวณโดยอัลกอริทึมขั้นสูงของฉัน เรารู้ว่าเราสามารถทำได้เนื่องจากการเพิ่มจำนวนลูปของลูปนอกสุดนั้นไม่มีผลต่อความถูกต้องของโซลูชัน ขั้นตอนนี้จริงลดคะแนนสุดท้ายของเราโดย 13 ดังนั้นจึงไม่ใช่ขั้นตอนเล็กน้อย

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