Game of Nim vs. Computer


Ok, so I had to create the game of nim for a homework assignment. It was for 2 human players. It was pretty easy and everything seems to work flawlessly except for probably some efficiency issues. My question is, what if I wanted to create the option to play the computer instead? There would be two modes, easy and hard. In easy mode, the computer would randomly choose the heap and the number of objects to remove from it. And in hard mode, the computer uses the idea of nim-sum and mathematical logic to win. So I think I undertand nim-sum, but I haven't the slightest idea of how to turn that logic into code. Any ideas? And thanks for the help.

(Also if you find anything wrong with what I've got right now and let me know that would be awesome.)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168

#include <iostream>
#include <iomanip>

using namespace std;

// Global constant
const int NUM_HEAPS = 3;    // Number of heaps

// FUNCTION PROTOTYPES GO HERE:

int prompt_heap(const int heap_number);		// argument heap_number is the heap number
bool nim_zero(const int heap[]);		// heap[] is the array that contains the number of objects in each heap
int change_player(int player);		// player is which player is in his/her turn (1 or 2)
void draw(const int objects);			// objects is the number of specified objects in the heap
void initialize_heap(int heap[]);		// heap[] is the array that contains the number of objects in each heap
void draw_heap(int heap[]);			// heap[] is the array that contains the number of objects in each heap
void move(int player, int heap[], int & rm_element, int & heap_number); 	// array heap[], the number of objects to remove, and the heap number
void heap_remove(int heap[], const int heap_number, const int rm_object);	// array heap[], the heap number, and the number of objects to remove from the specified heap
void winner(const int player);		// player is which player is in his/her turn (1 or 2)


int main()
{
  int heap[NUM_HEAPS];      // heap[i] = Number of elements in heap i
  int player(1);            // Player 1 or 2
  int heap_number(0);	// the heap number: 0, 1, or 2
  int remove_element(0);	// the number of elements to be removed from selected heap


  initialize_heap(heap);	// Read number of elements in each heap

  draw_heap(heap);		// Draw heaps as rows of *'s

  while (nim_zero(heap) != 1)	// WHILE some heap is not empty DO
  {
    move(player, heap, remove_element, heap_number);	// Read heap to modify and number of elements to remove from heap

    heap_remove(heap, heap_number, remove_element);	// Remove elements from heap

    if (nim_zero(heap) == true)	// IF all the heaps are empty, THEN
    {
      winner(player);	// Player has won - Print win message
    }
    else	// ELSE
    {
      draw_heap(heap);	// Play continues - Redraw heaps.

      player = change_player(player);	// Change to other player (new turn)
    }
  }
}

		 
// FUNCTION DEFINITIONS GO HERE:

void initialize_heap(int heap[])	// calls the function prompt_heap for the number of heaps there are
{
  for (int i = 0; i < NUM_HEAPS; i++)
  {
    heap[i] = prompt_heap(i);	// i represents the heap number
  } 
}


void draw_heap(int heap[])	// calls the function draw for the number of heaps there are
{
  cout << endl;
  for (int i = 0; i < NUM_HEAPS; i++)
  {
    cout << "Heap " << i << ": ";
    draw(heap[i]);
  }
  cout << endl;
}


int prompt_heap(const int heap_number)	// reads in the amount of objects in each heap from the user and initializes the heaps
{
  int x;
  cout << "How many objects are in heap " << heap_number << ": ";
  cin >> x;
 
  while (x <= 0 )
  {
    cout << "Sorry, the number of objects must be positive." << endl;
    cout << "How many objects are in heap " << heap_number << ": ";
    cin >> x;
  }
  return x;
}


void draw(const int objects)	// draws the number of objects of each heap onto the screen
{
  for (int i = 1; i <= objects; i++)
  {
    cout << "*";
  }
  cout << endl;
}


bool nim_zero(const int heap[])	// checks to see if the heaps have objects left or not
{
  for (int i = 0; i < NUM_HEAPS; i++)
  {
    if (heap[i] != 0) {return false;}
  }
  return true;
}


void move(int player, int heap[], int & rm_element, int & heap_number)	// the user picks what heap and how many objects to remove. Also controls associated error messages.
{
  cout << "Player (" << player << ") : Which heap would you like to play? ";
  cin >> heap_number;
  while (heap_number < 0 || heap_number > 2)
  {
    cout << "Invalid heap number. Please try again." << endl;
    cout << "Player (" << player << ") : Which heap would you like to play? ";
    cin >> heap_number;
  }
  while (heap[heap_number] == 0)
  {
    cout << "Heap " << heap_number << " has zero objects. Please select a different heap." << endl;
    cout << "Player (" << player << ") : Which heap would you like to play? ";
    cin >> heap_number;
  }
  cout << "Enter number of objects to remove (" << heap[heap_number] << " or less) from heap " << heap_number << ": ";
  cin >> rm_element;
  while (rm_element <= 0)
  {
    cout << "Number of objects you can remove must be positive. Try again." << endl;
    cout << "Enter number of objects to remove (" << heap[heap_number] << " or less) from heap " << heap_number << ": ";
    cin >> rm_element;
  }
  while (rm_element > heap[heap_number])
  {
    cout << "There are only " << heap[heap_number] << " elements in heap. Try again: ";
    cin >> rm_element;
  }
}


void heap_remove(int heap[], const int heap_number, const int rm_object)	// removes the chosen number of objects from the specified heap
{
  heap[heap_number] = heap[heap_number] - rm_object;
}


void winner(const int player)	// prints the winning player and message to the screen 
{
  cout << "Congratulations! Player " << player << " wins." << endl;
}


int change_player(int player)	// changes the player (next turn)
{
  if (player == 1) {return 2;}
  else if (player == 2) {return 1;}
  else
  {
    cout << "Player is wrong" << endl;
    return player;
  }
}
Topic archived. No new replies allowed.