Telif Hakkı 2021 TF-Agents Yazarları.
TensorFlow.org'da görüntüleyin | Google Colab'da çalıştırın | Kaynağı GitHub'da görüntüleyin | Not defterini indir |
Tanıtım
Takviye öğrenme algoritmaları, bir ortamda bir ilke yürütülürken deneyim yörüngelerini depolamak için yeniden yürütme arabelleklerini kullanır. Eğitim sırasında, aracının deneyimini "tekrar oynatmak" için yörüngelerin bir alt kümesi (sıralı bir alt küme veya bir örnek) için tekrar arabellekleri sorgulanır.
Bu ortak çalışmada, iki tür yeniden oynatma arabelleği keşfediyoruz: ortak bir API'yi paylaşan python destekli ve tensorflow destekli. Aşağıdaki bölümlerde API'yi, arabellek uygulamalarının her birini ve bunların veri toplama eğitimi sırasında nasıl kullanılacağını açıklıyoruz.
Kurmak
Henüz yapmadıysanız, tf-agent'ları yükleyin.
pip install tf-agents
from __future__ import absolute_import
from __future__ import division
from __future__ import print_function
import tensorflow as tf
import numpy as np
from tf_agents import specs
from tf_agents.agents.dqn import dqn_agent
from tf_agents.drivers import dynamic_step_driver
from tf_agents.environments import suite_gym
from tf_agents.environments import tf_py_environment
from tf_agents.networks import q_network
from tf_agents.replay_buffers import py_uniform_replay_buffer
from tf_agents.replay_buffers import tf_uniform_replay_buffer
from tf_agents.specs import tensor_spec
from tf_agents.trajectories import time_step
Tampon API'sini Tekrar Oynat
Replay Buffer sınıfı aşağıdaki tanım ve yöntemlere sahiptir:
class ReplayBuffer(tf.Module):
"""Abstract base class for TF-Agents replay buffer."""
def __init__(self, data_spec, capacity):
"""Initializes the replay buffer.
Args:
data_spec: A spec or a list/tuple/nest of specs describing
a single item that can be stored in this buffer
capacity: number of elements that the replay buffer can hold.
"""
@property
def data_spec(self):
"""Returns the spec for items in the replay buffer."""
@property
def capacity(self):
"""Returns the capacity of the replay buffer."""
def add_batch(self, items):
"""Adds a batch of items to the replay buffer."""
def get_next(self,
sample_batch_size=None,
num_steps=None,
time_stacked=True):
"""Returns an item or batch of items from the buffer."""
def as_dataset(self,
sample_batch_size=None,
num_steps=None,
num_parallel_calls=None):
"""Creates and returns a dataset that returns entries from the buffer."""
def gather_all(self):
"""Returns all the items in buffer."""
return self._gather_all()
def clear(self):
"""Resets the contents of replay buffer"""
Not tekrar tampon nesne başlatıldı zaman, ihtiyaç duyduğu data_spec
depolanması ki elementlerin. Bu spec karşılık TensorSpec
tamponu eklenir yörünge elemanları. Bu Spec genellikle vekilin bakarak elde edilir agent.collect_data_spec
(daha sonra bu konuda daha fazla) eğitim sırasında ajan tarafından beklenen şekiller, türleri ve yapıları tanımlar.
TFUniformReplayBuffer
TFUniformReplayBuffer
böylece biz burada Öğretici kullanacağız, TF-Agents en yaygın olarak kullanılan yeniden oynatma tampondur. Gelen TFUniformReplayBuffer
arka tampon bellek tensorflow değişkenler tarafından yapılan ve bu şekilde işlem grafik bir parçasıdır.
Tampon depolar elemanlarının toplu halde ve bir maksimum kapasitesi max_length
toplu kesimi başına elemanları. Bu durumda, toplam ara bellek kapasitesi batch_size
x max_length
elemanları. Tamponda depolanan öğelerin tümü eşleşen bir veri özelliğine sahip olmalıdır. Yeniden yürütme arabelleği veri toplama için kullanıldığında, belirtim aracının veri toplama özelliğidir.
Tampon oluşturma:
Bir oluşturmak için TFUniformReplayBuffer
biz geçmek:
- arabelleğin depolayacağı veri öğelerinin özelliği
-
batch size
tamponu yığın büyüklüğüne karşıt -
max_length
toplu kesimi başına elemanların sayısı
Burada oluşturma örneğidir TFUniformReplayBuffer
örnek veri özellikleri ile batch_size
32 ve max_length
1000 civarındadır.
data_spec = (
tf.TensorSpec([3], tf.float32, 'action'),
(
tf.TensorSpec([5], tf.float32, 'lidar'),
tf.TensorSpec([3, 2], tf.float32, 'camera')
)
)
batch_size = 32
max_length = 1000
replay_buffer = tf_uniform_replay_buffer.TFUniformReplayBuffer(
data_spec,
batch_size=batch_size,
max_length=max_length)
tampona yazma:
Tekrar tampon elemanları eklemek için, kullandığımız add_batch(items)
yöntemi items
öğe toplu temsil tensörlerinin bir liste / demet / yuva tamponuna ilave edilir. Her unsuru items
bir dış boyuta eşit olmalıdır batch_size
ve kalan boyutları (tekrar tampon yapıcıya iletilen veri özellikleri ile aynı) ürünün veri spec uymalıdır.
İşte toplu öğe eklemeye bir örnek
action = tf.constant(1 * np.ones(
data_spec[0].shape.as_list(), dtype=np.float32))
lidar = tf.constant(
2 * np.ones(data_spec[1][0].shape.as_list(), dtype=np.float32))
camera = tf.constant(
3 * np.ones(data_spec[1][1].shape.as_list(), dtype=np.float32))
values = (action, (lidar, camera))
values_batched = tf.nest.map_structure(lambda t: tf.stack([t] * batch_size),
values)
replay_buffer.add_batch(values_batched)
tampondan okuma
Veri okumak için üç yolu vardır TFUniformReplayBuffer
:
-
get_next()
- döner tampon bir numune. Örnek parti boyutu ve döndürülen zaman adımları sayısı, bu yöntemin bağımsız değişkenleri aracılığıyla belirtilebilir. -
as_dataset()
- bir şekilde tekrar tampon dönertf.data.Dataset
. Daha sonra bir veri kümesi yineleyicisi oluşturulabilir ve arabellekteki öğelerin örnekleri arasında yinelenebilir. -
gather_all()
- şekli ile döner bir Tensörün tamponun tüm öğeleri[batch, time, data_spec]
Aşağıda, bu yöntemlerin her birini kullanarak yeniden oynatma arabelleğinden nasıl okunacağına ilişkin örnekler verilmiştir:
# add more items to the buffer before reading
for _ in range(5):
replay_buffer.add_batch(values_batched)
# Get one sample from the replay buffer with batch size 10 and 1 timestep:
sample = replay_buffer.get_next(sample_batch_size=10, num_steps=1)
# Convert the replay buffer to a tf.data.Dataset and iterate through it
dataset = replay_buffer.as_dataset(
sample_batch_size=4,
num_steps=2)
iterator = iter(dataset)
print("Iterator trajectories:")
trajectories = []
for _ in range(3):
t, _ = next(iterator)
trajectories.append(t)
print(tf.nest.map_structure(lambda t: t.shape, trajectories))
# Read all elements in the replay buffer:
trajectories = replay_buffer.gather_all()
print("Trajectories from gather all:")
print(tf.nest.map_structure(lambda t: t.shape, trajectories))
WARNING:tensorflow:From /tmp/ipykernel_15476/1348928897.py:7: ReplayBuffer.get_next (from tf_agents.replay_buffers.replay_buffer) is deprecated and will be removed in a future version. Instructions for updating: Use `as_dataset(..., single_deterministic_pass=False) instead. WARNING:tensorflow:From /tmpfs/src/tf_docs_env/lib/python3.7/site-packages/tensorflow/python/data/experimental/ops/counter.py:66: scan (from tensorflow.python.data.experimental.ops.scan_ops) is deprecated and will be removed in a future version. Instructions for updating: Use `tf.data.Dataset.scan(...) instead Iterator trajectories: [(TensorShape([4, 2, 3]), (TensorShape([4, 2, 5]), TensorShape([4, 2, 3, 2]))), (TensorShape([4, 2, 3]), (TensorShape([4, 2, 5]), TensorShape([4, 2, 3, 2]))), (TensorShape([4, 2, 3]), (TensorShape([4, 2, 5]), TensorShape([4, 2, 3, 2])))] WARNING:tensorflow:From /tmp/ipykernel_15476/1348928897.py:24: ReplayBuffer.gather_all (from tf_agents.replay_buffers.replay_buffer) is deprecated and will be removed in a future version. Instructions for updating: Use `as_dataset(..., single_deterministic_pass=True)` instead. Trajectories from gather all: (TensorShape([32, 6, 3]), (TensorShape([32, 6, 5]), TensorShape([32, 6, 3, 2])))
PyUniformReplayBuffer
PyUniformReplayBuffer
aynı fonksiyonel olarak var TFUniformReplayBuffer
yerine tf değişkenler, veri numpy diziler depolanır. Bu arabellek, grafik dışı veri toplama için kullanılabilir. Yedekleme deposunun numpy'de olması, bazı uygulamaların Tensorflow değişkenlerini kullanmadan veri işlemeyi (öncelikleri güncellemek için dizin oluşturma gibi) yapmasını kolaylaştırabilir. Ancak bu uygulama, Tensorflow ile grafik optimizasyonlarının avantajına sahip olmayacak.
Aşağıda başlatmasını bir örnektir PyUniformReplayBuffer
ajanın politikası yörünge specs:
replay_buffer_capacity = 1000*32 # same capacity as the TFUniformReplayBuffer
py_replay_buffer = py_uniform_replay_buffer.PyUniformReplayBuffer(
capacity=replay_buffer_capacity,
data_spec=tensor_spec.to_nest_array_spec(data_spec))
Eğitim sırasında tekrar arabelleklerini kullanma
Artık bir tekrar arabelleği oluşturmayı, ona öğeler yazmayı ve ondan okuma yapmayı bildiğimize göre, aracılarımızın eğitimi sırasında yörüngeleri depolamak için kullanabiliriz.
Veri toplama
İlk olarak, veri toplama sırasında tekrar arabelleğinin nasıl kullanılacağına bakalım.
TF-Agents biz bir kullanma Driver
bir ortamda toplama deneyimine (diğer ayrıntılar için Sürücü öğretici bakınız). Bir kullanmak için Driver
, biz belirtmek Observer
için bir işlevdir Driver
bir yörünge aldığında yürütülecek.
Bu nedenle, tekrar tampon yörünge elemanları eklemek için, biz aramaları bu bir gözlemci eklemek add_batch(items)
tekrar tampon öğelerin bir toplu ekleyin.
Aşağıda bu bir örnektir TFUniformReplayBuffer
. Önce bir ortam, bir ağ ve bir aracı oluşturuyoruz. Sonra bir oluşturmak TFUniformReplayBuffer
. Yeniden yürütme arabelleğindeki yörünge öğelerinin özelliklerinin, aracının veri toplama özelliğine eşit olduğuna dikkat edin. Sonra onun set add_batch
veriler eğitim sırasında toplamak yapacak sürücü için gözlemci olarak yöntemini:
env = suite_gym.load('CartPole-v0')
tf_env = tf_py_environment.TFPyEnvironment(env)
q_net = q_network.QNetwork(
tf_env.time_step_spec().observation,
tf_env.action_spec(),
fc_layer_params=(100,))
agent = dqn_agent.DqnAgent(
tf_env.time_step_spec(),
tf_env.action_spec(),
q_network=q_net,
optimizer=tf.compat.v1.train.AdamOptimizer(0.001))
replay_buffer_capacity = 1000
replay_buffer = tf_uniform_replay_buffer.TFUniformReplayBuffer(
agent.collect_data_spec,
batch_size=tf_env.batch_size,
max_length=replay_buffer_capacity)
# Add an observer that adds to the replay buffer:
replay_observer = [replay_buffer.add_batch]
collect_steps_per_iteration = 10
collect_op = dynamic_step_driver.DynamicStepDriver(
tf_env,
agent.collect_policy,
observers=replay_observer,
num_steps=collect_steps_per_iteration).run()
Bir tren adımı için veri okuma
Yeniden yürütme arabelleğine yörünge öğeleri ekledikten sonra, bir tren adımı için giriş verileri olarak kullanmak üzere yeniden yürütme arabelleğinden yörünge yığınlarını okuyabiliriz.
Bir eğitim döngüsünde tekrar arabelleğinden yörüngeler üzerinde nasıl eğitileceğine dair bir örnek:
# Read the replay buffer as a Dataset,
# read batches of 4 elements, each with 2 timesteps:
dataset = replay_buffer.as_dataset(
sample_batch_size=4,
num_steps=2)
iterator = iter(dataset)
num_train_steps = 10
for _ in range(num_train_steps):
trajectories, _ = next(iterator)
loss = agent.train(experience=trajectories)
WARNING:tensorflow:From /tmpfs/src/tf_docs_env/lib/python3.7/site-packages/tensorflow/python/util/dispatch.py:206: calling foldr_v2 (from tensorflow.python.ops.functional_ops) with back_prop=False is deprecated and will be removed in a future version. Instructions for updating: back_prop=False is deprecated. Consider using tf.stop_gradient instead. Instead of: results = tf.foldr(fn, elems, back_prop=False) Use: results = tf.nest.map_structure(tf.stop_gradient, tf.foldr(fn, elems))