코드 참고 : 첫번째 훈련 - Codetorial
1.배경
인공지능은 간단하게 보면 함수를 만드는 것.
입력층 -> 은닉층 -> 출력층
목표 : CartPole 게임을 오래 하는 인공지능 만들기
-> 더 구체적으로는 현재 CartPole의 state를 입력하면, 왼쪽으로 이동하는게 좋을지 오른쪽으로 이동하는게 좋을지 알려주는 행동가치함수 Q(s)를 만드는 것 (s라는 상황에서 왼쪽으로 이동했을 때의 보상과 오른쪽으로 이동했을 때의 보상을 출력)
즉 Q(s)의 출력은 크기가 2인 1차원 배열.
이때 Q(s,a)는 Q(s)에서 a라는 행동을 했을 때의 행동가치.
이때 학습을 위해서는 2가지가 필요함
1.입력 데이터 (state 즉 상황)
2.입력 데이터에 따른 올바른 출력 데이터
우리는 2번째, 올바른 출력 데이터를 알 수가 없는 상황 -> 우리가 올바른 출력값을 계속 근사하면서 학습해야함
근사를 우리는 Q-러닝을 이용해서 함
Q_t(s,a) = Reward(즉각적인 보상) + r(감가율)*max(Q_t+1(next_s))
즉 s라는 상황에서 a라는 행동을 했을 때의 즉각적인 보상 + 다음상황에서 행동가치함수의 최대값*감가율 이다.
이때 당연히 Q_t+1(next_s)또한 정확히 알 수 없으므로, 실제 코드에서는 학습중인 인공신경망 모델을 사용해서 예측한 값을 사용한다.
2.구현
CartPole-v0에 관한 설명
CartPole에서의 state는 4가지 요소가 있음.
1.카트의 위치
2.카트의 속도
3.기울어진 각
4.기우는 각속도
따라서 입력 레이어 크기가 4임
또한 action은 2개가 있음
0 : 왼쪽으로 이동
1 : 오른쪽으로 이동
따라서 출력 레이어 크기가 2임
움직이는 방법 : env.step(0또는 1)
영상이 프레임 단위로 되듯이 여기는 스텝 단위로 움직임
다음 스텝에 뭘할지는 env.step()이라는 함수를 통해서 정할 수 있음.
이때 env.step()함수는 [state, reward, done, info] 배열을 반환함
state : 위에서 말한 4가지 요소
reward : 밖에 안 나가거나, 일정 이상으로 안 기울어지면 1, 아니면 0
done : 게임 종료 여부
info : 기타 정보들
env = gym.make('CartPole-v0') : CartPole을 할 수 있는 환경 만들기
env.reset() : 게임을 초기화. 이때 초기 state 반환
아래의 코드에서는 입실론-그리디 방법을 사용해서, 초기에는 랜덤하게 이동하도록 하다가 점점 입실론 값을 줄여서 학습한대로 이동하게끔 만듬
import gym
import tensorflow as tf
import numpy as np
import random
from collections import deque
env = gym.make('CartPole-v0') # 카트폴이라는 환경 받아오기
#모델 만들기. 4 * 24 * 24 * 2
model = tf.keras.models.Sequential([
tf.keras.layers.Dense(24, input_dim=4, activation=tf.nn.relu),
tf.keras.layers.Dense(24, activation=tf.nn.relu),
tf.keras.layers.Dense(2, activation='linear')
])
model.compile(optimizer=tf.keras.optimizers.Adam(lr=0.01),
loss='mean_squared_error',
#learning_rate=0.001
)
score = []
memory = deque(maxlen=2000)
#에피소드 1000번 반복
for i in range(1000):
state = env.reset() #초기 상태 저장
state = np.reshape(state,[1,4]) #state input에 사용해야하므로 1*4 행렬로 변경
eps = 1 / (i /50 + 10) #입실론 값은 학습할 수록 0에 가까워짐
#200타임 이동
for t in range(200):
if np.random.rand() < eps: #탐험
action = np.random.randint(0, 2)
else: #예측대로
predict = model.predict(state)
action = np.argmax(predict)
next_state, reward, done, _ = env.step(action) #다음 상태, 보상 저장
next_state = np.reshape(next_state, [1, 4]) #다음 상태도 다시 인풋으로 활용해야하므로 1*4행렬로 변경
memory.append((state, action, reward, next_state, done)) #현재상태, 현재액션, 보상, 다음상태 memory에 저장
state = next_state #state -> next_state로 변경
if done or t == 199: #종료되었을 경우
print('Episode', i, 'Score', t + 1)
score.append(t + 1)
break
if i > 10: #에피소드 10 이후 부터 학습 (그 전까지는 미니배치를 위한 데이터 추출)
minibatch = random.sample(memory, 16) #memory에 저장된 데이터 중 16개 뽑음
for state, action, reward, next_state, done in minibatch: #minibatch에 있는 데이터 16개로 학습
target = reward #reward가 목표
if not done: #게임오버가 안되었을 경우 (잘한 행동일 경우)
target = reward + 0.9 * np.amax(model.predict(next_state)[0]) #state에서 action에 대한 가치 Q = 즉각적 보상 + 감가율*다음 state의 Q_t+1
target_outputs = model.predict(state) #Q(s) 예측
target_outputs[0][action] = target #Q(s)의 출력들 중 에서, 내가 선택한 action의 예측값(Q(s,a)의 값은 위에서 계산한 걸로 바꿈
model.fit(state, target_outputs, epochs=1, verbose=0) #입력데이터와 예측한 출력데이터로 학습 시키기
env.close()
print(score)
'인공지능 > 강화학습' 카테고리의 다른 글
HungryCat강화학습3 - BC + DQN 알고리즘 (with ML-Agent) (0) | 2023.08.05 |
---|---|
HungryCat 강화학습2 - DQN 알고리즘 (with ML-Agent) (0) | 2023.08.03 |
HungryCat 강화학습1 - A2C 알고리즘 (with ML-Agent) (0) | 2023.08.03 |
REINFORCE 알고리즘을 이용한 CartPole 강화학습 (0) | 2023.06.10 |