swttt-gem 0.7.0 → 0.8.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.7.0
1
+ 0.8.0
data/lib/board.rb CHANGED
@@ -1,11 +1,11 @@
1
1
  class Board
2
- attr_reader :game_history, :dimension, :game_board, :player_value, :board,
3
- :row_scores, :column_scores, :left_diagonal_score, :right_diagonal_score
2
+ attr_reader :game_history, :game_board, :player_value, :board, :row_scores,
3
+ :column_scores, :left_diagonal_score, :right_diagonal_score
4
4
 
5
5
  def initialize(dimension = 3)
6
6
  @dimension = dimension
7
- @game_history, @board = [], [[0,0,0],[0,0,0],[0,0,0]]
8
- @row_scores, @column_scores = [0,0,0], [0,0,0]
7
+ @game_history, @board = [], Array.new(@dimension) {Array.new(@dimension) {0}}
8
+ @row_scores, @column_scores = Array.new(@dimension) {0}, Array.new(@dimension) {0}
9
9
  @left_diagonal_score, @right_diagonal_score = 0, 0
10
10
  end
11
11
 
@@ -33,6 +33,10 @@ class Board
33
33
  @game_history.size == @dimension*@dimension
34
34
  end
35
35
 
36
+ def dimension
37
+ @dimension-1
38
+ end
39
+
36
40
  def player_value
37
41
  value = -(number_of_moves_made % 2)
38
42
  value = 1 if value.zero?
@@ -40,7 +44,7 @@ class Board
40
44
  end
41
45
 
42
46
  def print
43
- (0...@dimension).each { |row| print_row(row) }
47
+ (0..@dimension).each { |row| print_row(row) }
44
48
  puts "\n"
45
49
  end
46
50
 
@@ -48,7 +52,7 @@ private
48
52
 
49
53
  def print_row(row)
50
54
  puts "\n"
51
- (0...@dimension).each { |column| print_square(row, column) }
55
+ (0..@dimension).each { |column| print_square(row, column) }
52
56
  end
53
57
 
54
58
  def print_square(row, column)
@@ -63,7 +67,7 @@ private
63
67
  @row_scores[row] += update_value
64
68
  @column_scores[column] += update_value
65
69
  @left_diagonal_score += update_value if row == column
66
- @right_diagonal_score += update_value if row == @dimension - column - 1
70
+ @right_diagonal_score += update_value if row == dimension - column
67
71
  end
68
72
  end
69
73
 
data/lib/game_observer.rb CHANGED
@@ -14,21 +14,25 @@ class GameObserver
14
14
 
15
15
  private
16
16
 
17
- def loop_array
18
- (0...@game_board.dimension).each { |index| return true if yield(index) == @game_board.dimension }
19
- false
20
- end
21
-
22
17
  def horizontal_win?
23
- loop_array { |row| @game_board.row_scores[row].abs }
18
+ check_for_winner { |row| @game_board.row_scores[row].abs }
24
19
  end
25
20
 
26
21
  def vertical_win?
27
- loop_array { |column| @game_board.column_scores[column].abs }
22
+ check_for_winner { |column| @game_board.column_scores[column].abs }
28
23
  end
29
24
 
30
25
  def diagonal_win?
31
- (@game_board.left_diagonal_score.abs == @game_board.dimension ||
32
- @game_board.right_diagonal_score.abs == @game_board.dimension)
26
+ (is_a_win?(@game_board.left_diagonal_score.abs) ||
27
+ is_a_win?(@game_board.right_diagonal_score.abs))
28
+ end
29
+
30
+ def check_for_winner
31
+ (0..@game_board.dimension).each { |index| return true if is_a_win?(yield(index)) }
32
+ false
33
+ end
34
+
35
+ def is_a_win?(value)
36
+ value == @game_board.dimension+1
33
37
  end
34
38
  end
@@ -3,9 +3,9 @@ class MinimaxComputer
3
3
  def initialize(board, observer)
4
4
  @game_board, @observer = board, observer
5
5
  @first_move = [Move.new(0,0),
6
- Move.new(0,@game_board.dimension-1),
7
- Move.new(@game_board.dimension-1,0),
8
- Move.new(@game_board.dimension-1, @game_board.dimension-1)]
6
+ Move.new(0,@game_board.dimension),
7
+ Move.new(@game_board.dimension,0),
8
+ Move.new(@game_board.dimension, @game_board.dimension)]
9
9
  @my_player_value = @game_board.player_value
10
10
  end
11
11
 
@@ -29,12 +29,21 @@ private
29
29
  end
30
30
 
31
31
  def select_first_move
32
- if !@first_move.include?(@game_board.game_history.first)
33
- move = @first_move[rand(@first_move.size)]
34
- else
35
- middle = @game_board.dimension/2
36
- move = Move.new(middle, middle)
37
- end
32
+ return corner_move if all_board_corners_open?
33
+ return middle_move
34
+ end
35
+
36
+ def all_board_corners_open?
37
+ !@first_move.include?(@game_board.game_history.first)
38
+ end
39
+
40
+ def corner_move
41
+ @first_move[rand(@first_move.size)]
42
+ end
43
+
44
+ def middle_move
45
+ middle = @game_board.dimension/2
46
+ return move = Move.new(middle, middle)
38
47
  end
39
48
 
40
49
  def perform_mini_max(iteration)
@@ -43,13 +52,13 @@ private
43
52
  for_each_cell { |row, column| best_moves.add_better_move(best_moves.value, calculate_path_score(row, column,iteration),
44
53
  Move.new(row, column)) if @game_board.is_empty_at?(row, column) }
45
54
  return best_moves.value if !iteration.zero?
46
- move = best_moves.random
55
+ move = best_moves.get_random_move
47
56
  @game_board.move(move.row, move.column)
48
57
  end
49
58
 
50
59
  def for_each_cell
51
- (0...@game_board.dimension).each do |row|
52
- (0...@game_board.dimension).each { |column| yield(row, column) }
60
+ (0..@game_board.dimension).each do |row|
61
+ (0..@game_board.dimension).each { |column| yield(row, column) }
53
62
  end
54
63
  end
55
64
 
@@ -90,7 +99,7 @@ class BestMove
90
99
  @game_board, @my_player_value = game_board, my_player_value
91
100
  end
92
101
 
93
- def random
102
+ def get_random_move
94
103
  @moves[rand(@moves.size)]
95
104
  end
96
105
 
data/spec/board_spec.rb CHANGED
@@ -6,9 +6,9 @@ describe Board do
6
6
  @my_board = Board.new
7
7
  end
8
8
 
9
- def double_loop
10
- (0...@my_board.dimension).each do |row|
11
- (0...@my_board.dimension).each do |column|
9
+ def iterate_board
10
+ (0..@my_board.dimension).each do |row|
11
+ (0..@my_board.dimension).each do |column|
12
12
  yield(row, column)
13
13
  end
14
14
  end
@@ -19,7 +19,7 @@ describe Board do
19
19
  end
20
20
 
21
21
  it "should check for a full board" do
22
- double_loop { |row, column| @my_board.move(row, column) }
22
+ iterate_board { |row, column| @my_board.move(row, column) }
23
23
  @my_board.full?.should == true
24
24
  end
25
25
 
@@ -8,32 +8,32 @@ describe GameObserver do
8
8
  @observer = GameObserver.new(@my_board)
9
9
  end
10
10
 
11
- def loop
12
- (0...@my_board.dimension).each { |position| yield(position) }
11
+ def iterate_row_or_column
12
+ (0..@my_board.dimension).each { |position| yield(position) }
13
13
  end
14
14
 
15
15
  it "detects a horizontal win" do
16
- loop { |column| @my_board.move(0,column,1) }
16
+ iterate_row_or_column { |column| @my_board.move(0,column,1) }
17
17
  @observer.has_winner?.should == true
18
18
  end
19
19
 
20
20
  it "detects a vertical win" do
21
- loop { |row| @my_board.move(row,0,1) }
21
+ iterate_row_or_column { |row| @my_board.move(row,0,1) }
22
22
  @observer.has_winner?.should == true
23
23
  end
24
24
 
25
25
  it "detects a left diagonal win" do
26
- loop { |position| @my_board.move(position,position,1) }
26
+ iterate_row_or_column { |position| @my_board.move(position,position,1) }
27
27
  @observer.has_winner?.should == true
28
28
  end
29
29
 
30
30
  it "detects a right diagonal win" do
31
- loop { |position| @my_board.move(@my_board.dimension-position-1,position,1) }
31
+ iterate_row_or_column { |position| @my_board.move(@my_board.dimension-position,position,1) }
32
32
  @observer.has_winner?.should == true
33
33
  end
34
34
 
35
35
  it "detects if the game is over" do
36
- loop { |row| loop { |column| @my_board.move(row, column, 2) } }
36
+ iterate_row_or_column { |row| iterate_row_or_column { |column| @my_board.move(row, column, 2) } }
37
37
  @observer.game_over?.should == true
38
38
  end
39
39
  end
data/swttt-gem.gemspec CHANGED
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = %q{swttt-gem}
8
- s.version = "0.7.0"
8
+ s.version = "0.8.0"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["Stephen Walker"]
12
- s.date = %q{2011-05-04}
12
+ s.date = %q{2011-05-09}
13
13
  s.description = %q{TTT Gem}
14
14
  s.email = %q{stephenwalker1988@gmail.com}
15
15
  s.extra_rdoc_files = [
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: swttt-gem
3
3
  version: !ruby/object:Gem::Version
4
- hash: 3
4
+ hash: 63
5
5
  prerelease:
6
6
  segments:
7
7
  - 0
8
- - 7
8
+ - 8
9
9
  - 0
10
- version: 0.7.0
10
+ version: 0.8.0
11
11
  platform: ruby
12
12
  authors:
13
13
  - Stephen Walker
@@ -15,7 +15,7 @@ autorequire:
15
15
  bindir: bin
16
16
  cert_chain: []
17
17
 
18
- date: 2011-05-04 00:00:00 -05:00
18
+ date: 2011-05-09 00:00:00 -05:00
19
19
  default_executable:
20
20
  dependencies:
21
21
  - !ruby/object:Gem::Dependency