結果

問題 No.157 2つの空洞
ユーザー conf8oconf8o
提出日時 2020-04-10 16:48:02
言語 Swift
(5.8.1)
結果
AC  
実行時間 76 ms / 2,000 ms
コード長 3,632 bytes
コンパイル時間 8,729 ms
コンパイル使用メモリ 184,204 KB
実行使用メモリ 13,908 KB
最終ジャッジ日時 2023-08-20 14:39:38
合計ジャッジ時間 4,263 ms
ジャッジサーバーID
(参考情報)
judge15 / judge14
このコードへのチャレンジ(β)

テストケース

テストケース表示
入力 結果 実行時間
実行使用メモリ
testcase_00 AC 6 ms
13,412 KB
testcase_01 AC 7 ms
13,256 KB
testcase_02 AC 6 ms
13,304 KB
testcase_03 AC 6 ms
13,152 KB
testcase_04 AC 6 ms
13,264 KB
testcase_05 AC 7 ms
13,172 KB
testcase_06 AC 7 ms
13,380 KB
testcase_07 AC 6 ms
13,256 KB
testcase_08 AC 7 ms
13,560 KB
testcase_09 AC 6 ms
13,432 KB
testcase_10 AC 7 ms
13,684 KB
testcase_11 AC 10 ms
13,796 KB
testcase_12 AC 7 ms
13,396 KB
testcase_13 AC 7 ms
13,660 KB
testcase_14 AC 41 ms
13,424 KB
testcase_15 AC 16 ms
13,548 KB
testcase_16 AC 15 ms
13,908 KB
testcase_17 AC 76 ms
13,512 KB
testcase_18 AC 10 ms
13,408 KB
testcase_19 AC 7 ms
13,484 KB
権限があれば一括ダウンロードができます

ソースコード

diff #

import Foundation

public struct Deque<T> {
  private var array: [T?]
  private var head: Int
  private var capacity: Int
  private let originalCapacity: Int

  public init(_ capacity: Int = 10) {
    self.capacity = max(capacity, 1)
    originalCapacity = self.capacity
    array = [T?](repeating: nil, count: capacity)
    head = capacity
  }

  public var isEmpty: Bool {
    return count == 0
  }

  public var count: Int {
    return array.count - head
  }

  public mutating func enqueue(_ element: T) {
    array.append(element)
  }

  public mutating func enqueueFront(_ element: T) {
    if head == 0 {
      capacity *= 2
      let emptySpace = [T?](repeating: nil, count: capacity)
      array.insert(contentsOf: emptySpace, at: 0)
      head = capacity
    }

    head -= 1
    array[head] = element
  }

  public mutating func dequeue() -> T? {
    guard head < array.count, let element = array[head] else { return nil }

    array[head] = nil
    head += 1

    if capacity >= originalCapacity && head >= capacity*2 {
      let amountToRemove = capacity + capacity/2
      array.removeFirst(amountToRemove)
      head -= amountToRemove
      capacity /= 2
    }
    return element
  }

  public mutating func dequeueBack() -> T? {
    if isEmpty {
      return nil
    } else {
      return array.removeLast()
    }
  }

  public func peekFront() -> T? {
    if isEmpty {
      return nil
    } else {
      return array[head]
    }
  }

  public func peekBack() -> T? {
    if isEmpty {
      return nil
    } else {
      return array.last!
    }
  }
}

func readInt() -> [Int] {
    return readLine()!.split(separator: " ").map{Int($0)!}
}

let line = readInt()
let W = line[0]
let H = line[1]
let maze = (1...H).map { _ in Array(readLine()!) }
let directions = [(1,0),(0,1),(-1,0),(0,-1)]

func holeCheck(_ y: Int, _ x: Int, _ hole: Set<[Int]>) -> Bool {
    return y < 0 || y >= H || x < 0 || x >= W || maze[y][x] == "#" || hole.contains([y, x])
}

func gridCheck(_ y: Int, _ x: Int, _ hole: Set<[Int]>) -> Bool {
    return y < 0 || y >= H || x < 0 || x >= W || hole.contains([y, x])
}

func bfs(_ initial: [Int], _ hole: inout Set<[Int]>, _ goal: (Int, Int) -> Bool, _ isOut: (Int, Int, Set<[Int]>) -> Bool) -> Int {
    var queue = Deque<[Int]>()
    queue.enqueue(initial)
    var explored = Set<[Int]>()
    explored.insert([initial[0], initial[1]])
    hole.insert([initial[0], initial[1]])
    while let yx = queue.dequeue() {
        let y = yx[0]
        let x = yx[1]
        let count = yx[2]
        for d in directions {
            let y_ = d.0 + y
            let x_ = d.1 + x
            
            if goal(y_, x_) {
                return count
            }

            if isOut(y_, x_, hole) || explored.contains([y_, x_]){
                continue
            }

            hole.insert([y_, x_])
            explored.insert([y_, x_])
            queue.enqueue([y_, x_, count+1])
        }
    }
    return 401
}

func main() {

    var holes = [Set<[Int]>(), Set<[Int]>()]
    var count = 0
    for i in 1..<(H-1) {
        for j in 1..<(W-1) {
            if holes.allSatisfy({!$0.contains([i, j])}) && maze[i][j] == "." {
                let _ = bfs([i,j,0], &holes[count], { _, _ in false }, holeCheck)
                count += 1
            }
            if count > 1 { break }
        }
        if count > 1 { break }
    }
    
    
    var ans = 401
    for yx in holes[0] {
        var s = Set<[Int]>()
        let res = bfs([yx[0], yx[1], 0], &s, { holes[1].contains([$0, $1]) }, gridCheck)
        if res < ans {
           ans = res
        }
    }
    
    print(ans)
}

main()
0