- Notifications
You must be signed in to change notification settings - Fork 2
Expand file tree
/
Copy pathRLBrain.py
More file actions
Latest commit
95 lines (82 loc) · 4.02 KB
/
Copy pathRLBrain.py
File metadata and controls
95 lines (82 loc) · 4.02 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
importnumpyasnp
importpandasaspd
importmath
##class that holds the reinforcement learning for our program.
#
classRLBrain:
MIN_EXP=0.01
MIN_LEARN=0.1
##Constructor:-
#Takes in the list of actions, and sets the decay, learn, and random rates.
def__init__(self, reduced_actions=None, decay_rate=0.1):
"""The init method for the brain.
actions is a list of actions detailed in Botty_McBotface.py
I am implementing the QTable as a pandas DataFrame. This is to easily index our Q-table with strings.
"""
self.actions=reduced_actions# list of actions
self.QTable=pd.DataFrame(columns=self.actions, dtype=np.float64)
self.learn_rate=self.learning(0)
self.decay_rate=decay_rate
self.rand_rate=self.explore(0)
## Chooses which action to carry out.
# @param self Object pointer calling the function.
# @param state Gamestate information.
# @return The chosen action.
defchoose_action(self, state):
"""This method chooses which action to do. This method assume check for new states first.
:returns an action."""
# .loc constructs a series of action q vales, .idmax() returns the index of the max in a series.
# The Q values are index by actions in the series, so we return the max action.
ifnp.random.uniform() <self.rand_rate:
returnnp.random.choice(self.actions)
else:
returnself.QTable.loc[state, :].idxmax()
## Gets a new state + reward.
# @param self Object pointer calling the function.
# @param state Gamestate information.
defadd_state(self, state):
"""This method gets new state and reward from the environment """
ifstatenotinself.QTable.index:
# appends an empty list of labeled floats to the table
self.QTable=self.QTable.append(
pd.Series(data=np.zeros(len(self.actions)), index=self.actions, name=state))
## Finds the rate at which random states are chosen.
# @param self Object pointer calling the function.
# @param t Number of states explored so far.
defexplore(self, t):
returnmax(self.MIN_EXP, min(1.0, 1-math.log10((t+1) /25)))
## Finds the rate at which the RL bot learns.
# @param self Object pointer calling the function.
# @param t Number of states explored so far.
deflearning(self, t):
returnmax(self.MIN_LEARN, min(1.0, 1-math.log10((t+1) /25)))
## Learns the value of a state transition, stores it in q-table.
# @param self Object pointer calling the function.
# @param state First of the two states in the state transition being learned.
# @param next_state Second of the two states in the state transition being learned.
# @param action Action that was taken that transitioned between the two states.
# @param reward Reward for the action.
deflearn(self, state, next_state, action, reward):
"""This method will use the given information to update the q-table."""
q_value=self.QTable.at[state, action]
# using pd.series.max to get q-value.
q_target=reward+self.decay_rate*self.QTable.loc[next_state, :].max()
self.QTable.at[state, action] +=self.learn_rate* (q_target-q_value)
## Reads a QTable from a file for the RL bot.
# @param self Object pointer calling the function.
# @filename Name of the file being read from.
defread_from_file_QT(self, filename):
self.QTable=pd.read_csv(filename, index_col=0)
## Allows us to store a QTable in a file.
# @param self Object pointer calling the function.
# @param filename Name of the file being written to.
defwrite_to_file_QT(self, filename):
self.QTable.to_csv(filename)
## Gets the size of the current QTable.
# @param self Object pointer calling the function.
defget_size(self):
print(self.QTable.shape)
defread_from_file_states(self, filename):
pass
defwrite_to_file_states(self, filename):
pass