-
Notifications
You must be signed in to change notification settings - Fork 3
Expand file tree
/
Copy pathnim.cpp
More file actions
152 lines (141 loc) · 3.69 KB
/
nim.cpp
File metadata and controls
152 lines (141 loc) · 3.69 KB
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
#include <iostream>
#include <stdlib.h>
/* written by martin scharm
* see http://binfalse.de
*
* you have to take a various number of o's
* from *one* of the stacks. if you did so,
* the artificial intelligence will do the
* same. winner is the one who clears the
* last stack! so think about before doing ;)
*/
void err (std::string s)
{
std::cout << s << std::endl;
std::cout << "USAGE:" << std::endl << "\t-n\tnumber of stacks [2..30]" << std::endl << "\t-m\tmaximal stack size [5..50]" << std::endl;
exit (1);
}
void help ()
{
std::cout << "written by martin scharm" << std::endl;
std::cout << "see https://binfalse.de" << std::endl << std::endl;
std::cout << "you have to take a various number of o's" << std::endl;
std::cout << "from *one* of the stacks. if you did so," << std::endl;
std::cout << "the artificial intelligence will do the" << std::endl;
std::cout << "same. winner is the one who clears the" << std::endl;
std::cout << "last stack! so think about before doing ;)" << std::endl;
err ("");
}
void draw (int *stacks, int num)
{
std::cout << std::endl << "----------------------------------------" << std::endl << "stack\tsize" << std::endl;
for (int i = 0; i < num; i++)
{
std::cout << i << ":\t";
for (int j = 0; j < stacks[i]; j++)
std::cout << 'o';
std::cout << " (" << stacks[i] << ")" << std::endl;
}
std::cout << "----------------------------------------" << std::endl;
}
void inform (bool player)
{
if (player)
std::cout << "wow, gratz! lucky punch or a systematic win?" << std::endl;
else
std::cout << "haha, no chance against cpu's?" << std::endl;
}
bool playersTurn (int *stacks, int num)
{
int a = 0, s = -1;
while (s < 0 || s >= num || stacks[s] < 1)
{
draw (stacks, num);
std::cout << "which stack? (0.." << num - 1 << ") ";
std::cin >> s;
}
while (a < 1 || a > stacks[s])
{
draw (stacks, num);
std::cout << "how much from stack " << s << "? (1.." << stacks[s] << ") ";
std::cin >> a;
}
stacks[s] -= a;
if (stacks[s] == 0)
{
for (int i = 0; i < num; i++)
if (stacks[i] != 0) return false;
return true;
}
return false;
}
bool artisTurn (int *stacks, int num)
{
int sum = stacks[0], a = 0, s = -1;
for (int i = 1; i < num; i++)
sum = sum xor stacks[i];
if (sum != 0)
for (int i = 0; i < num; i++)
{
int tmp = sum xor stacks[i];
if (tmp < stacks[i])
{
s = i;
a = stacks[i] - tmp;
}
}
while (s < 0 || s >= num || stacks[s] < 1) s = rand () % num;
while (a < 1 || a > stacks[s]) a = 1 + (rand () % stacks[s]);
stacks[s] -= a;
std::cout << std::endl << ">>>>>> the artificial intelligence took " << a << " o's from stack " << s << std::endl;
if (stacks[s] == 0)
{
for (int i = 0; i < num; i++)
if (stacks[i] != 0) return false;
return true;
}
return false;
}
int main (int argc, char **argv)
{
int numStacks = 5, maxStackSize = 10, *stacks;
bool player = true, fin = false;
for (int i = 1; i < argc; i++)
{
std::string a = argv[i];
if (i + 1 < argc)
{
if (a == "-n")
{
numStacks = atoi (argv[i+1]);
i++;
continue;
}
if (a == "-m")
{
maxStackSize = atoi (argv[i+1]);
i++;
continue;
}
}
if (a == "-h" || a == "--help")
{
help ();
}
}
if (numStacks < 2 || numStacks > 30) err ("number of stacks should be in [2..30]");
if (maxStackSize < 5 || maxStackSize > 50) err ("maximum stack size should be in [5..50]");
srand (time (0));
stacks = new int [numStacks];
for (int i = 0; i < numStacks; i++)
stacks[i] = 1 + (rand () % maxStackSize);
while (!fin)
{
if (player) fin = playersTurn (stacks, numStacks);
else fin = artisTurn (stacks, numStacks);
if (fin) inform (player);
player = !player;
}
std::cout << "done.." << std::endl;
return 0;
}