ruby 作为对https://practicingruby.com/articles/meditations-on-bad-and-good-code-1 artice的冥想,这是我第一次尝试重构

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了ruby 作为对https://practicingruby.com/articles/meditations-on-bad-and-good-code-1 artice的冥想,这是我第一次尝试重构相关的知识,希望对你有一定的参考价值。

module TicTacToe
  class Game
    def self.play
      new.run
    end

    def players
      @players ||= %w(X O).cycle
    end

    def board
      @board ||= Board.new
    end

    def run
      play_turn until board.finished?(@current_player)
    end

    def play_turn
      advance_turn
      make_move(read_move)
    end

    def advance_turn
      @current_player = players.next
    end

    def make_move(move)
      board.set(move.row, move.col, move.player)
    end

    def read_move
      loop do
        board.draw
        move = Move.read(@current_player)
        return move if valid? move
      end
    end

    def valid?(move)
      move.valid? && board.free?(move.row, move.col)
    end
  end

  class Move < Struct.new(:row, :col, :player);
    def valid?
      row && col
    end

    def self.read(player)
      row,col = gets.split.map(&:to_i)
      new(row, col, player)
    end
  end

  class Board
    FREE = ' '
    def initialize
      @rows ||= Array.new(3) { Array.new(3){ FREE } }
    end

    def set(row, col, player)
      @rows[row][col] = player
    end

    def draw
      puts "\n  0 1 2"
      puts @rows.map.with_index{ |row, x| "#{x}:#{row * "|"}" } * "\n"
      print "\nrow col >> "
    end

    def free?(row, col)
      @rows.fetch(row).fetch(col) == FREE
    rescue IndexError
      puts 'Out of bounds'
      false
    end

    def finished?(player)
      full? || tic_tac_toe?(player)
    end

    def full?
      @rows.flatten.none?{|c| c == FREE }
    end

    def tic_tac_toe?(player)
      lines.any? {|line| line.all? { |cell| cell == player }}
    end

    def lines
      rows + cols + diagonals
    end

    def rows
      @rows
    end

    def cols
      @rows.transpose
    end

    def diagonals
      [
        (0..2).map{|d| @rows[d][d] },
        (0..2).map{|d| @rows[d][2-d] }
      ]
    end
  end
end

if __FILE__ == $PROGRAM_NAME
  TicTacToe::Game.play
end

以上是关于ruby 作为对https://practicingruby.com/articles/meditations-on-bad-and-good-code-1 artice的冥想,这是我第一次尝试重构的主要内容,如果未能解决你的问题,请参考以下文章

ruby 符号作为键,但无法从哈希中获取值

Android - Ruby on Rails - MySQL

ruby hash

如何为第三方 Ruby 脚本包含 Gem

ruby 这是Ruby中的Guess游戏,只是为了好玩,并将Head First Ruby中的Chap1作为参考:)

有没有办法在 Ruby YAML 文件中指定 ruby​​ 类/模块常量作为值