swttt-gem 1.1.0 → 1.2.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 +1 -1
- data/lib/abcomputer.rb +65 -0
- data/lib/board.rb +1 -1
- data/lib/minimax_computer.rb +3 -3
- data/spec/minimax_computer_spec.rb +18 -3
- data/swttt-gem.gemspec +3 -2
- metadata +5 -4
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
1.
|
1
|
+
1.2.0
|
data/lib/abcomputer.rb
ADDED
@@ -0,0 +1,65 @@
|
|
1
|
+
class ABComputer
|
2
|
+
def initialize
|
3
|
+
|
4
|
+
end
|
5
|
+
|
6
|
+
def make_move
|
7
|
+
alpha = (-1.0)/(0.0)
|
8
|
+
beta = (1.0)/(0.0)
|
9
|
+
best_score = nil
|
10
|
+
iterate_board do |row, column|
|
11
|
+
@board.make_move(row, column)
|
12
|
+
path_score = get_max(1, alpha, beta)
|
13
|
+
@board.undo_move
|
14
|
+
if best_score.nil? || path_score > best_score
|
15
|
+
best_row = row
|
16
|
+
best_column = column
|
17
|
+
best_score = path_score
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
22
|
+
def get_max(depth, alpha, beta)
|
23
|
+
iterate_board do |row, column|
|
24
|
+
if alpha > beta
|
25
|
+
return alpha
|
26
|
+
else
|
27
|
+
if @board.is_empty_at(row, column)
|
28
|
+
@board.move(row, column)
|
29
|
+
if @observer.game_over?
|
30
|
+
return -@board.player_value if @observer.has_winner?
|
31
|
+
return 0
|
32
|
+
else
|
33
|
+
value = get_min(depth+1, alpha, beta)
|
34
|
+
alpha = value if alpha < value
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
40
|
+
|
41
|
+
def get_min(depth, alpha, beta)
|
42
|
+
iterate_board do |row, column|
|
43
|
+
if alpha < beta
|
44
|
+
return beta
|
45
|
+
else
|
46
|
+
if @board.is_empty_at(row, column)
|
47
|
+
@board.move(row, column)
|
48
|
+
if @observer.game_over?
|
49
|
+
return -@board.player_value if @observer.has_winner?
|
50
|
+
return 0
|
51
|
+
else
|
52
|
+
value = get_max(depth+1, alpha, beta)
|
53
|
+
beta = value if beta > value
|
54
|
+
end
|
55
|
+
end
|
56
|
+
end
|
57
|
+
end
|
58
|
+
end
|
59
|
+
|
60
|
+
private
|
61
|
+
|
62
|
+
def iterate_board
|
63
|
+
(1..3).each { |row| (1..3).each { |column| yield(row, column) } }
|
64
|
+
end
|
65
|
+
end
|
data/lib/board.rb
CHANGED
data/lib/minimax_computer.rb
CHANGED
@@ -63,15 +63,15 @@ private
|
|
63
63
|
end
|
64
64
|
|
65
65
|
def calculate_score(iteration)
|
66
|
-
if
|
66
|
+
if immediate_win_or_loss?(iteration)
|
67
67
|
return infinity
|
68
68
|
else
|
69
69
|
return perform_mini_max(iteration + 1)
|
70
70
|
end
|
71
71
|
end
|
72
72
|
|
73
|
-
def
|
74
|
-
iteration
|
73
|
+
def immediate_win_or_loss?(iteration)
|
74
|
+
iteration<2 && @observer.has_winner?
|
75
75
|
end
|
76
76
|
|
77
77
|
def infinity
|
@@ -26,13 +26,28 @@ describe MinimaxComputer do
|
|
26
26
|
end
|
27
27
|
|
28
28
|
it "takes an immediate win" do
|
29
|
-
@my_board.move(1
|
29
|
+
@my_board.move(2,1)
|
30
|
+
@my_board.move(3,3)
|
30
31
|
@my_board.move(2,2)
|
32
|
+
@my_board.move(2,3)
|
31
33
|
@my_board.move(1,1)
|
32
|
-
@my_board.move(1,2)
|
33
|
-
@my_board.move(0,0)
|
34
34
|
@computer.move
|
35
35
|
@observer.has_winner?.should be_true
|
36
36
|
@my_board.number_of_moves_made.should == 6
|
37
37
|
end
|
38
|
+
|
39
|
+
it "takes a corner or middle piece for first move" do
|
40
|
+
@my_board.move(2,3)
|
41
|
+
@computer.move
|
42
|
+
[Move.new(1,1), Move.new(1,3), Move.new(3,1),
|
43
|
+
Move.new(3,3)].include?(@my_board.game_history.last).should be_true
|
44
|
+
end
|
45
|
+
|
46
|
+
it "blocks immediate losses" do
|
47
|
+
@my_board.move(2,3)
|
48
|
+
@computer.move
|
49
|
+
@my_board.move(1,3)
|
50
|
+
@computer.move
|
51
|
+
@my_board.value_at(3,3).should == -1
|
52
|
+
end
|
38
53
|
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 = "1.
|
8
|
+
s.version = "1.2.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-
|
12
|
+
s.date = %q{2011-05-19}
|
13
13
|
s.description = %q{TTT Gem}
|
14
14
|
s.email = %q{stephenwalker1988@gmail.com}
|
15
15
|
s.extra_rdoc_files = [
|
@@ -26,6 +26,7 @@ Gem::Specification.new do |s|
|
|
26
26
|
"Rakefile",
|
27
27
|
"VERSION",
|
28
28
|
"lib/.DS_Store",
|
29
|
+
"lib/abcomputer.rb",
|
29
30
|
"lib/board.rb",
|
30
31
|
"lib/game_observer.rb",
|
31
32
|
"lib/human_player.rb",
|
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:
|
4
|
+
hash: 31
|
5
5
|
prerelease:
|
6
6
|
segments:
|
7
7
|
- 1
|
8
|
-
-
|
8
|
+
- 2
|
9
9
|
- 0
|
10
|
-
version: 1.
|
10
|
+
version: 1.2.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-
|
18
|
+
date: 2011-05-19 00:00:00 -05:00
|
19
19
|
default_executable:
|
20
20
|
dependencies:
|
21
21
|
- !ruby/object:Gem::Dependency
|
@@ -97,6 +97,7 @@ files:
|
|
97
97
|
- Rakefile
|
98
98
|
- VERSION
|
99
99
|
- lib/.DS_Store
|
100
|
+
- lib/abcomputer.rb
|
100
101
|
- lib/board.rb
|
101
102
|
- lib/game_observer.rb
|
102
103
|
- lib/human_player.rb
|