Initial commit

master
Simeon Keske 5 years ago
commit 9825def253
No known key found for this signature in database
GPG Key ID: B15B623C3C45B235

2
.gitignore vendored

@ -0,0 +1,2 @@
*.fiar
__pycache__

@ -0,0 +1,43 @@
import fiar
import nn
import lib
game = fiar.FIAR();
nn = lib.loadSingle(0)
def declareWinner():
game.printField();
print("And the winner is P", game.proveWinner(), "!")
def isnumber(val):
try:
val = int(val)
return True
except ValueError:
return False
while True:
game.printField();
player_input = input("P1, where do you put your stone? ")
while not (isnumber(player_input) and 7 >= int(player_input) >= 1):
player_input = input("P1, your input has to be a number between 1 and 7! New input: ")
try:
game.setStone(int(player_input)-1, 1)
except OverflowError:
print("This Column is already full, maybe try again next time...")
if(game.proveWinner()):
declareWinner()
break
# --------------- #
game = lib.nextNNmove(nn, game, 2);
if(game.proveWinner()):
declareWinner()
break

@ -0,0 +1,51 @@
import fiar
game = fiar.FIAR();
def declareWinner():
game.printField();
print("And the winner is P", game.proveWinner(), "!")
def isnumber(val):
try:
val = int(val)
return True
except ValueError:
return False
while True:
game.printField();
player_input = input("P1, where do you put your stone? ")
while not (isnumber(player_input) and 7 >= int(player_input) >= 1):
player_input = input("P1, your input has to be a number between 1 and 7! New input: ")
try:
game.setStone(int(player_input)-1, 1);
except OverflowError:
print("This Column is already full, maybe try again next time...")
if(game.proveWinner()):
declareWinner()
break
# --------------- #
game.printField();
player_input = input("P2, where do you put your stone? ")
while not (isnumber(player_input) and 7 >= int(player_input) >= 1):
player_input = input("P2, your input has to be a number between 1 and 7! New input: ")
try:
game.setStone(int(player_input)-1, 2);
except OverflowError:
print("This Column is already full, maybe try again next time...")
if(game.proveWinner()):
declareWinner()
break

@ -0,0 +1,121 @@
class FIAR():
def __init__(self, height=6, width=7):
self.height = height # y
self.width = width # x
self.field = []
# field[x][y]
for x in range(width):
col = []
for y in range(height):
col.append(None)
self.field.append(col)
def getTransformedField(self):
output = []
for col in self.field:
output += col
return output
def printField(self):
redBG = "\33[41m"
greenBG = "\33[42m"
clearBG = "\33[0m"
dashes = (self.width * 2)+1
print("-" * dashes)
for y in range(self.height, -1, -1):
for x in range(self.width):
if y == self.height:
print("|" + str(x+1), end='')
elif self.field[x][y] == 1:
print("|" + redBG + "x" + clearBG, end='')
elif self.field[x][y] == 2:
print("|" + greenBG+"o" + clearBG, end='')
else:
print("|" + " ", end='')
print("|")
print("-" * dashes)
def setStone(self, col, player):
if(col in list(range(self.width))):
has_set = False
for i in range(self.height):
if self.field[col][i] == None:
self.field[col][i] = player
has_set = True
break
if not has_set:
raise OverflowError
else:
raise IndexError
def proveWinner(self):
# Tie:
tie = True
for x in range(self.width):
if(self.field[x][self.height-1] == None):
tie = False
break
if tie:
return 3
# Horizontal:
for y in range(self.height):
for x in range(self.width-3):
if self.field[x][y] != None:
first = self.field[x][y]
isWinner = True
for i in range(1, 4):
if self.field[x+i][y] != first:
isWinner = False
break
if isWinner:
return first
# Vertical:
for x in range(self.width):
for y in range(self.height-3):
if self.field[x][y] != None:
first = self.field[x][y]
isWinner = True
for i in range(1, 4):
if self.field[x][y+i] != first:
isWinner = False
break
if isWinner:
return first
# Diagonal Up:
for x in range(self.width-3):
for y in range(self.height-3):
if self.field[x][y] != None:
first = self.field[x][y]
isWinner = True
for i in range(1, 4):
if self.field[x+i][y+i] != first:
isWinner = False
break
if isWinner:
return first
# Diagonal Down:
for x in range(3, self.width):
for y in range(self.height-3):
if self.field[x][y] != None:
first = self.field[x][y]
isWinner = True
for i in range(1, 4):
if self.field[x-i][y+i] != first:
isWinner = False
break
if isWinner:
return first
return False

@ -0,0 +1,58 @@
import nn
import pickle
networks_filename = "networks.fiar"
def nextNNmove(network, game, player):
flatfield = game.getTransformedField()
player1 = []
player2 = []
for spot in flatfield:
if spot == 1:
player1.append(1)
player2.append(0)
elif spot == 2:
player1.append(0)
player2.append(1)
else:
player1.append(0)
player2.append(0)
out = network.calculateOutput(player1+player2)
preferences = []
for i in range(len(out)):
maxI = 0
maxVal = -20
for j in range(len(out)):
if out[j] > maxVal:
maxVal = out[j]
maxI = j
out[maxI] = -20
preferences.append(maxI)
for val in preferences:
try:
game.setStone(val, player)
except OverflowError:
pass
else:
break
return game
def createAndSave(num):
nets = []
for i in range(num):
nets.append(nn.NN(84, 168, 168, 84, 84, 42, 7))
saveAll(nets)
def saveAll(nets):
with open(networks_filename, 'wb') as networks_file:
pickle.dump(nets, networks_file)
def loadAll():
with open(networks_filename, 'rb') as networks_file:
nets = pickle.load(networks_file)
return nets
def loadSingle(num):
return loadAll()[num]

40
nn.py

@ -0,0 +1,40 @@
import numpy as np
class NN():
score = 0
def __init__(self, *args):
self.layers = args
self.synapses = []
for i in range(len(self.layers)-1):
self.synapses.append(np.random.normal(scale=1,size=(self.layers[i], self.layers[i+1])))
def calculateOutput(self, input):
layerInput = input
for synapseLayer in self.synapses:
layerInput = np.dot(layerInput, synapseLayer)
layerInput = self.sigmoid(layerInput)
return layerInput
def sigmoid(self, s):
#print("Arr:", arr)
#s = np.array(arr)
# activation function
res = 1 / (1 + np.exp(-s))
#print("Res:", res)
return res
def getSynapses(self):
return self.synapses
def setSynapses(self, synapses):
self.synapses = synapses
def mutate(self, val):
mut_arr = []
for i in range(len(self.layers)-1):
mut_arr.append(np.random.normal(scale=val,size=(self.layers[i], self.layers[i+1])))
self.synapses = np.add(self.synapses, mut_arr)
return mut_arr

@ -0,0 +1,2 @@
numpy
pickle

@ -0,0 +1,63 @@
import lib, fiar
nets = lib.loadAll()
gen = 0
def NvN(net1, net2, printField=False):
game = fiar.FIAR();
while True:
game = lib.nextNNmove(net1, game, 1);
if(game.proveWinner()):
break
game = lib.nextNNmove(net2, game, 2);
if(game.proveWinner()):
break
if printField:
game.printField()
print(net1.synapses[0][0][0])
print()
return game.proveWinner()
try:
while True:
gen += 1
print("Gen:", gen)
# Reset the nets' score:
for net in nets:
net.score = 0
# Let the nets play against each other:
for i in range(len(nets)):
for j in range(i+1, len(nets)):
winner = NvN(nets[i], nets[j], i==0 and j==1)
#print("Net1:",i,"Net2:",j)
#print("Winner:",winner)
if(winner == 1):
nets[i].score += 1
if(winner == 2):
nets[j].score += 1
winner = NvN(nets[j], nets[i])
#print("Net1:",i,"Net2:",j)
#print("Winner:",winner)
if(winner == 1):
nets[i].score += 1
if(winner == 2):
nets[j].score += 1
# Sort the nets by their score:
nets.sort(key=lambda x: x.score, reverse=True)
for i in range(int(len(nets)/3)):
nets[i+int(len(nets)/3)] = nets[i];
nets[i+int(len(nets)/3)].mutate(0.001);
nets[i+int(len(nets)/3*2)] = nets[i];
nets[i+int(len(nets)/3*2)].mutate(0.1);
except KeyboardInterrupt:
print("Saving all Data...")
lib.saveAll(nets)
Loading…
Cancel
Save