python neural-network tensorflow deep-learning q-learning

python - ¿Por qué mi Deep Q Network no domina un simple Gridworld(Tensorflow)?(Como evaluar una Deep-Q-Net)



neural-network deep-learning (3)

Así que hace bastante tiempo escribí esta pregunta, pero parece que todavía hay bastante interés y solicitud para el código en ejecución. Finalmente decidí crear un repositorio de github.

Ya que hace bastante tiempo lo escribí y así sucesivamente no se agotará, pero no debería ser tan difícil hacerlo funcionar. Así que aquí está la red q profunda y el ejemplo que escribí en el momento en que funcionaba entonces, espero que lo disfruten: Enlace al repositorio q profundo

¡Sería bueno ver alguna contribución y si lo arregla y lo hace funcionar, haga una solicitud de extracción!

Intento familiarizarme con Q-learning y Deep Neural Networks, actualmente intento implementar Atari con Deep Reinforcement Learning .

Para probar mi implementación y jugar con ella, me di cuenta de que probé un simple gridworld. Donde tengo una cuadrícula de N x N, comienzo en la esquina superior izquierda y termina en la parte inferior derecha. Las acciones posibles son: izquierda, arriba, derecha, abajo.

A pesar de que mi implementación se ha vuelto muy similar a this (espero que sea buena) parece que no aprendió nada. Mirando los pasos totales que necesita terminar (supongo que el promedio sería de 500 con un tamaño de cuadrícula de 10x10, pero también valores muy bajos y altos), me parece más aleatorio que cualquier otra cosa.

Lo probé con y sin capas convolucionales y jugué con todos los parámetros, pero para ser honesto, no tengo idea si algo con mi implementación está mal o si necesita entrenar más tiempo (lo dejo entrenar durante bastante tiempo) o qué. siempre. Pero al menos parece que convergen, aquí la trama de la pérdida valora una sesión de entrenamiento:

Entonces, ¿cuál es el problema en este caso?

Pero también, y quizás más importante, cómo puedo "depurar" este Deep-Q-Nets, en el entrenamiento supervisado hay conjuntos de entrenamiento, prueba y validación y, por ejemplo, con precisión y recuperación es posible evaluarlos. ¿Qué opciones tengo para el aprendizaje sin supervisión con Deep-Q-Nets, de modo que la próxima vez quizás pueda solucionarlo yo mismo?

Finalmente aquí está el código:

Esta es la red:

ACTIONS = 5 # Inputs x = tf.placeholder(''float'', shape=[None, 10, 10, 4]) y = tf.placeholder(''float'', shape=[None]) a = tf.placeholder(''float'', shape=[None, ACTIONS]) # Layer 1 Conv1 - input with tf.name_scope(''Layer1''): W_conv1 = weight_variable([8,8,4,8]) b_conv1 = bias_variable([8]) h_conv1 = tf.nn.relu(conv2d(x, W_conv1, 5)+b_conv1) # Layer 2 Conv2 - hidden1 with tf.name_scope(''Layer2''): W_conv2 = weight_variable([2,2,8,8]) b_conv2 = bias_variable([8]) h_conv2 = tf.nn.relu(conv2d(h_conv1, W_conv2, 1)+b_conv2) h_conv2_max_pool = max_pool_2x2(h_conv2) # Layer 3 fc1 - hidden 2 with tf.name_scope(''Layer3''): W_fc1 = weight_variable([8, 32]) b_fc1 = bias_variable([32]) h_conv2_flat = tf.reshape(h_conv2_max_pool, [-1, 8]) h_fc1 = tf.nn.relu(tf.matmul(h_conv2_flat, W_fc1)+b_fc1) # Layer 4 fc2 - readout with tf.name_scope(''Layer4''): W_fc2 = weight_variable([32, ACTIONS]) b_fc2 = bias_variable([ACTIONS]) readout = tf.matmul(h_fc1, W_fc2)+ b_fc2 # Training with tf.name_scope(''training''): readout_action = tf.reduce_sum(tf.mul(readout, a), reduction_indices=1) loss = tf.reduce_mean(tf.square(y - readout_action)) train = tf.train.AdamOptimizer(1e-6).minimize(loss) loss_summ = tf.scalar_summary(''loss'', loss)

Y aquí el entrenamiento.

# 0 => left # 1 => up # 2 => right # 3 => down # 4 = noop ACTIONS = 5 GAMMA = 0.95 BATCH = 50 TRANSITIONS = 2000 OBSERVATIONS = 1000 MAXSTEPS = 1000 D = deque() epsilon = 1 average = 0 for episode in xrange(1000): step_count = 0 game_ended = False state = np.array([0.0]*100, float).reshape(100) state[0] = 1 rsh_state = state.reshape(10,10) s = np.stack((rsh_state, rsh_state, rsh_state, rsh_state), axis=2) while step_count < MAXSTEPS and not game_ended: reward = 0 step_count += 1 read = readout.eval(feed_dict={x: [s]})[0] act = np.zeros(ACTIONS) action = random.randint(0,4) if len(D) > OBSERVATIONS and random.random() > epsilon: action = np.argmax(read) act[action] = 1 # play the game pos_idx = state.argmax(axis=0) pos = pos_idx + 1 state[pos_idx] = 0 if action == 0 and pos%10 != 1: #left state[pos_idx-1] = 1 elif action == 1 and pos > 10: #up state[pos_idx-10] = 1 elif action == 2 and pos%10 != 0: #right state[pos_idx+1] = 1 elif action == 3 and pos < 91: #down state[pos_idx+10] = 1 else: #noop state[pos_idx] = 1 pass if state.argmax(axis=0) == pos_idx and reward > 0: reward -= 0.0001 if step_count == MAXSTEPS: reward -= 100 elif state[99] == 1: # reward & finished reward += 100 game_ended = True else: reward -= 1 s_old = np.copy(s) s = np.append(s[:,:,1:], state.reshape(10,10,1), axis=2) D.append((s_old, act, reward, s)) if len(D) > TRANSITIONS: D.popleft() if len(D) > OBSERVATIONS: minibatch = random.sample(D, BATCH) s_j_batch = [d[0] for d in minibatch] a_batch = [d[1] for d in minibatch] r_batch = [d[2] for d in minibatch] s_j1_batch = [d[3] for d in minibatch] readout_j1_batch = readout.eval(feed_dict={x:s_j1_batch}) y_batch = [] for i in xrange(0, len(minibatch)): y_batch.append(r_batch[i] + GAMMA * np.max(readout_j1_batch[i])) train.run(feed_dict={x: s_j_batch, y: y_batch, a: a_batch}) if epsilon > 0.05: epsilon -= 0.01

¡Aprecio cada ayuda e ideas que pueda tener!


He implementado un DQN de juguete simple sin capas CNN, y funciona. Aquí hay algunos hallazgos durante mi implementación, espero que ayude.

  1. De acuerdo con el documento de DeepMind que no usaron la capa de agrupación máxima, la razón es que la imagen se volverá invariante en la posición, lo que no es bueno para el juego. La posición del agente es crucial para la información del juego. Arquitectura DQN

  2. Si desea omitir el entorno de gimnasio de CNN, use por primera vez (como lo que he hecho para la implementación del juguete), durante mi desarrollo, aquí hay algunas cosas que encontré:

    • Codifique su estado de entorno mediante la codificación de una sola aplicación, aumentará la eficiencia de la capacitación.
    • Solo uso una matriz de pesos con forma de [número de estado, número de acción], para hacer la multiplicación de la matriz con el estado de entrada codificada en caliente. Sin sesgo, sin función de activación (aumentará el tiempo de entrenamiento, supongo, nunca funcionará después de agregar otra capa o algo).

Estas son dos cosas que encontré extremadamente cruciales para que mi implementación funcione, no entiendo completamente la razón detrás de esto, espero que mi respuesta pueda darles un poco de información.


Para aquellos interesados, ajusté aún más los parámetros y el modelo, pero la mayor mejora fue el cambio a una red de avance simple con 3 capas y aproximadamente 50 neuronas en la capa oculta. Para mí entonces convergió en un tiempo bastante decente.

Por cierto, se aprecian más consejos para la depuración!