Class: XO::Evaluator

Inherits:
Object
  • Object
show all
Includes:
Singleton
Defined in:
lib/xo/evaluator.rb

Overview

Evaluator is a Singleton that defines an #analyze method than can be used to examine a grid to answer the following questions:

  1. Is it a valid grid? A grid is considered valid if it possible for two players, taking turns, to reach the given grid configuration.

  2. Is there a winner/loser or is the grid squashed?

  3. Who is the winner/loser?

  4. Which positions make up the winning row, column and/or diagonal?

Class Method Summary collapse

Instance Method Summary collapse

Class Method Details

.xos(grid) ⇒ Array(Integer, Integer)

Returns the number of Grid::X‘s and Grid::O’s in the given grid.

Examples:

g = Grid.new('xoxxo')
xs, os = Evaluator.xos(g)
puts xs # => 3
puts os # => 2

Returns:

  • (Array(Integer, Integer))


77
78
79
80
81
82
83
84
85
86
# File 'lib/xo/evaluator.rb', line 77

def self.xos(grid)
  xs = os = 0

  grid.each do |_, _, k|
    xs += 1 if k == Grid::X
    os += 1 if k == Grid::O
  end

  [xs, os]
end

Instance Method Details

#analyze(grid, token) ⇒ Hash

Examines the given grid assuming that the given token is the one that was last placed on it.

The following return values are possible:

  • If everything is fine, then

    { status: :ok }
    
  • If the game is over and the given token is in a winning position, then

    { status: :game_over, type: :winner, details: [{ where: :where, index: :index, positions: :positions }] }
    
  • If the game is over and the other token is in a winning position, then

    { status: :game_over, type: :loser, details: [{ where: :where, index: :index, positions: :positions }] }
    
  • If the game is over due to a squashed grid, then

    { status: :game_over, type: :squashed }
    
  • If there is too much of one token, then

    { status: :invalid_grid, type: :too_many_moves_ahead }
    
  • If both tokens are arranged in winning positions, then

    { status: :invalid_grid, type: :two_winners }
    

Legend:

  • :where is one of :row, :column, :diagonal

  • :index is one of 1, 2, 3 if :where is :row or :column and one of 1, 2 if :where is :diagonal

  • :positions is a 3 element array having the row, column values of the winning position

Notice that the :details key is an Array since it is possible to win a game in two different ways. For example:

 x | o | x
---+---+---
 o | x | o
---+---+---
 x | o | x

Parameters:

  • grid (Grid)

    the grid to be examined

  • token (Grid::X, Grid::O)

    the token that was last placed on the grid

Returns:

  • (Hash)

Raises:



62
63
64
65
66
# File 'lib/xo/evaluator.rb', line 62

def analyze(grid, token)
  check_token(token)
  initialize_analyzer(grid, token)
  perform_analysis
end