いものやま。

雑多な知識の寄せ集め

変種オセロをSwiftに移植してみた。(その7)

ボードの実装が終わったので、次はボードの表示の実装。

ボードの表示

さっそくコードを。

/* BoardViewer.swift */

import Foundation

public struct BoardViewer {
    private static let COL_INDEX = "     1   2   3   4   5   6   7   8   9"
    private static let LINE      = "   +---+---+---+---+---+---+---+---+---+"

  public static func view(board: Board) {
    println(String(format: "[%03d] turn: %@, token: %@",
            board.move, BoardViewer.mark(board.turn), BoardViewer.mark(board.token)))
    println(BoardViewer.COL_INDEX)
    println(BoardViewer.LINE)
    for row in Board.ROW_MIN...Board.ROW_MAX {
      print(" \(row) ")
      for col in Board.COL_MIN...Board.COL_MAX {
        let color = board.color(row, col)
        print("| \(BoardViewer.mark(color)) ")
      }
      println("|")
      println(BoardViewer.LINE)
    }
  }

  public static func mark(color: Board.Color) -> String {
    assert(
      color != .WALL, 
      "invalid color. [color: \(color)]")

    switch color {
    case .EMPTY:
      return " "
    case .BLACK:
      return "O"
    case .GRAY:
      return "-"
    case .WHITE:
      return "X"
    default:
      return " "
    }
  }

  private init?() {
    return nil
  }
}

SwiftだとRubyのモジュールのようなものはないので、BoardViewerは構造体として、ボードを表示する機能はタイプメソッドとして実装した。

一つポイントとなるのが、Foundationをインポートしているところ。
これは、NSString#init(format: String, _: Any...)を使うため。
(※ドキュメントにはNSString#init(format: String, arguments: CVaListPointer)と書かれていたけど、外部引数名でargumentsを指定すると上手くいかなかった)
NSStringとStringには対応関係があり、Foundationをインポートすることで、NSStringのメソッドも使えるようになる。

ただ、ちょっと気をつけないといけない(というか自分がミスった)のが、文字列を置き換える部分のフォーマットがC言語風の%sでなく、Objective-C風の%@ということ。 まぁ、理屈は分かるんだけど、ちょっと、ね。

あと、オブジェクトを作れないように、イニシャライザをprivateにしている。

プレイグラウンドでの実行

ここまで作ると、プレイグラウンドで試しに使ってみることが出来る。

まずは、Swiftをプレイグラウンドで使ってみた。 - いものやま。で説明した通り、サポートコードとしてボードの実装とボードの表示の実装を突っ込む。
シンボリックリンクを張るのが一番簡単)

f:id:yamaimo0625:20150623141055p:plain

そしたら、プレイグラウドでボードのオブジェクトを生成して、実際にプレイ、表示をさせてみる。

f:id:yamaimo0625:20150623141250p:plain

そうすると、こんな感じでタイムラインの「Console Output」にボードの様子が表示される。

今日はここまで!