I'm trying to do the game Snake using genetic algorithm and Keras.
My problem, right now, is the following:
I create the initial population of snake with X genes each, where X is NUMBER_WEIGHTS:
INPUT = 24
NEURONS_HIDDEN_1 = 16
NEURONS_HIDDEN_2 = 16
OUTPUT = 3
NUMBER_WEIGHTS = INPUT * NEURONS_HIDDEN_1 + NEURONS_HIDDEN_1 * NEURONS_HIDDEN_2 + NEURONS_HIDDEN_2 * OUTPUT
and i create the initial population like this:
population = numpy.random.choice(numpy.arange(-1, 1, step=0.01), size=(config.NUMBER_OF_POPULATION, config.NUMBER_WEIGHTS))
I have a for cycle that for each snake inside my population start the pygame script, inside the pygame script i have the Keras NN, but i would like to pass the weights that i have generated to the NN.
My NN is like that for now:
from keras.layers import Dense, Activation
from keras.models import Sequential
from keras.optimizers import SGD
from utils import config
def neural_net(weights):
model = Sequential()
model.add(Dense(config.INPUT, input_shape=(config.INPUT,)))
model.add(Activation('relu'))
# create the dense input layer
# model.add(Dense(config.INPUT, activation=keras.activations.relu(4,), input_dim=4))
# model.add(Activation('sigmoid'))
# create first hidden layer
model.add(Dense(config.NEURONS_HIDDEN_1, input_shape=(config.INPUT,)))
model.add(Activation('relu'))
# create second hidden layer
model.add(Dense(config.NEURONS_HIDDEN_2, input_shape=(config.NEURONS_HIDDEN_1,)))
model.add(Activation('relu'))
# create output layer
model.add(Dense(config.OUTPUT, input_shape=(config.NEURONS_HIDDEN_2,)))
model.add(Activation('softmax'))
print(weights.shape[0])
model.set_weights(weights)
# create the optimizer (Stochastic Gradient Descent)
sgd = SGD(lr=0.01, decay=0.0, momentum=0.0, nesterov=False)
# Use mean squared error loss and SGD as optimizer
model.compile(loss='mse', optimizer=sgd)
return model
But model.set_weights(weights) return this exception:
File "neural_network.py", line 28, in neural_net
model.set_weights(weights)
File "C:\Users\Davide\AppData\Local\Programs\Python\Python37\lib\site-packages\keras\engine\network.py", line 527, in set_weights
K.batch_set_value(tuples)
File "C:\Users\Davide\AppData\Local\Programs\Python\Python37\lib\site-packages\keras\backend\tensorflow_backend.py", line 2960, in batch_set_value
tf_keras_backend.batch_set_value(tuples)
File "C:\Users\Davide\AppData\Local\Programs\Python\Python37\lib\site-packages\tensorflow_core\python\keras\backend.py", line 3323, in batch_set_value
x.assign(np.asarray(value, dtype=dtype(x)))
File "C:\Users\Davide\AppData\Local\Programs\Python\Python37\lib\site-packages\tensorflow_core\python\ops\resource_variable_ops.py", line 819, in assign
self._shape.assert_is_compatible_with(value_tensor.shape)
File "C:\Users\Davide\AppData\Local\Programs\Python\Python37\lib\site-packages\tensorflow_core\python\framework\tensor_shape.py", line 1110, in assert_is_compatible_with
raise ValueError("Shapes %s and %s are incompatible" % (self, other))
ValueError: Shapes (24, 24) and () are incompatible
Process finished with exit code 1
We have 24 input * 16 neuros on the hidden layer one, then 16 neurons * 16 neurons on layer hidden 2 and finally 16 neurons hidden layer 2 * 3 inputs = 24*16+16*16+16*3 = 688
And
print(weights.shape[0])
is 688. So why i can't set the correct weights?
First time doing a project using AI, so i may have completely misunderstood how this works
I am sure there is a shape mismatch in the weights of model and the weights you are providing. You need to provide weights corresponding to each layer as shown in the example below.
import tensorflow as tf
mnist = tf.keras.datasets.mnist
(x_train, y_train),(x_test, y_test) = mnist.load_data()
x_train, x_test = x_train / 255.0, x_test / 255.0
def create_model():
model = tf.keras.models.Sequential([
tf.keras.layers.Flatten(input_shape=(28, 28),name='flatten'),
tf.keras.layers.Dense(128, activation='relu',name='dense1'),
tf.keras.layers.Dropout(0.2,name = 'dropout'),
tf.keras.layers.Dense(10, name='dense2')
])
model.compile(optimizer='adam',
loss=tf.keras.losses.SparseCategoricalCrossentropy(from_logits=True), #'sparse_categorical_crossentropy',
metrics=['accuracy'])
return model
# create model architecture and compile
model = create_model()
model.fit(x_train, y_train, epochs=5)
model.evaluate(x_test, y_test)
#saving weights
model.save_weights('./model_weights', save_format='tf')
#layer weights from the model
layer_dict = dict([(layer.name, layer) for layer in model.layers])
print(layer_dict)
# creating the same model architecture and compile
loaded_model = create_model()
# This initializes the variables used by the optimizers,
# as well as any stateful metric variables
loaded_model.train_on_batch(x_train[:1], y_train[:1])
# loading the weights from base_model
for layer in loaded_model.layers:
layer_name = layer.name
print(layer.name)
layer.set_weights(layer_dict[layer_name].get_weights())
# accessing weights of a layer by its name
layer_dict[layer_name].get_weights()
# check the evaluation before and after are same
loaded_model.evaluate(x_test, y_test)
print(loaded_model.weights)
print(model.weights)
Hope this example will give some insights for you to solve your problem.
Full code is here for your reference.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.