训练时第二个step loss特别大_RLlib训练APIs

在高层RLlib提供了Trainer类,他keep一个policy用于和环境交互。通过trainer接口,policy可以训练,保存,或者用于动作的计算。在多智能体训练中,trainer同时管理多个策略的查询和优化。

ad4ef1803cc42ca89a17ed99e956997c.png

你能使用下述命令训练一个DQN:

rllib train --run DQN --env CartPole-v0

结果会默认保存到子目录~/ray_results。这个子目录包含文件

params.json(用于保存超参数),

{
"env": "CartPole-v0"
}

文件result.json(包含了每个episode的训练数据)

{"episode_reward_max": 49.0, "episode_reward_min": 8.0, "episode_reward_mean": 20.74736842105263, "episode_len_mean": 20.74736842105263, "episodes_this_iter": 190, "policy_reward_mean": {}, "custom_metrics": {}, "sampler_perf": {"mean_env_wait_ms": 0.06072526728229897, "mean_processing_ms": 0.15717214266133053, "mean_inference_ms": 0.7396685669186922}, "off_policy_estimator": {}, "info": {"num_steps_trained": 3968, "num_steps_sampled": 4000, "sample_time_ms": 2006.434, "load_time_ms": 46.28, "grad_time_ms": 1630.859, "update_time_ms": 476.545, "learner": {"default_policy": {"cur_kl_coeff": 0.20000000298023224, "cur_lr": 4.999999873689376e-05, "total_loss": 64.50533294677734, "policy_loss": -0.03904179856181145, "vf_loss": 64.53799438476562, "vf_explained_var": 0.042524512857198715, "kl": 0.03189465031027794, "entropy": 0.6628726124763489, "entropy_coeff": 0.0}}}, "timesteps_this_iter": 4000, "done": false, "timesteps_total": 4000, "episodes_total": 190, "training_iteration": 1, "experiment_id": "78133ebfb69b4d1590b42716371ad75d", "date": "2019-08-24_15-16-13", "timestamp": 1566630973, "time_this_iter_s": 4.203403949737549, "time_total_s": 4.203403949737549, "pid": 3569, "hostname": "yang-XPS-15-9570", "node_ip": "183.173.87.224", "config": {"monitor": false, "log_level": "INFO", "callbacks": {"on_episode_start": null, "on_episode_step": null, "on_episode_end": null, "on_sample_end": null, "on_train_result": null, "on_postprocess_traj": null}, "ignore_worker_failures": false, "log_sys_usage": true, "model": {"conv_filters": null, "conv_activation": "relu", "fcnet_activation": "tanh", "fcnet_hiddens": [256, 256], "free_log_std": false, "no_final_linear": false, "vf_share_layers": true, "use_lstm": false, "max_seq_len": 20, "lstm_cell_size": 256, "lstm_use_prev_action_reward": false, "state_shape": null, "framestack": true, "dim": 84, "grayscale": false, "zero_mean": true, "custom_preprocessor": null, "custom_model": null, "custom_options": {}}, "optimizer": {}, "gamma": 0.99, "horizon": null, "soft_horizon": false, "env_config": {}, "env": "CartPole-v0", "clip_rewards": null, "clip_actions": true, "preprocessor_pref": "deepmind", "lr": 5e-05, "evaluation_interval": null, "evaluation_num_episodes": 10, "evaluation_config": {}, "num_workers": 2, "num_gpus": 0, "num_cpus_per_worker": 1, "num_gpus_per_worker": 0, "custom_resources_per_worker": {}, "num_cpus_for_driver": 1, "num_envs_per_worker": 1, "sample_batch_size": 200, "train_batch_size": 4000, "batch_mode": "truncate_episodes", "sample_async": false, "observation_filter": "NoFilter", "synchronize_filters": true, "tf_session_args": {"intra_op_parallelism_threads": 2, "inter_op_parallelism_threads": 2, "gpu_options": {"allow_growth": true}, "log_device_placement": false, "device_count": {"CPU": 1}, "allow_soft_placement": true}, "local_tf_session_args": {"intra_op_parallelism_threads": 8, "inter_op_parallelism_threads": 8}, "compress_observations": false, "collect_metrics_timeout": 180, "metrics_smoothing_episodes": 100, "remote_worker_envs": false, "remote_env_batch_wait_ms": 0, "min_iter_time_s": 0, "timesteps_per_iteration": 0, "seed": null, "input": "sampler", "input_evaluation": ["is", "wis"], "postprocess_inputs": false, "shuffle_buffer_size": 0, "output": null, "output_compress_columns": ["obs", "new_obs"], "output_max_file_size": 67108864, "multiagent": {"policies": {}, "policy_mapping_fn": null, "policies_to_train": null}, "use_gae": true, "lambda": 1.0, "kl_coeff": 0.2, "sgd_minibatch_size": 128, "shuffle_sequences": true, "num_sgd_iter": 30, "lr_schedule": null, "vf_share_layers": false, "vf_loss_coeff": 1.0, "entropy_coeff": 0.0, "entropy_coeff_schedule": null, "clip_param": 0.3, "vf_clip_param": 10.0, "grad_clip": null, "kl_target": 0.01, "simple_optimizer": false}, "time_since_restore": 4.203403949737549, "timesteps_since_restore": 4000, "iterations_since_restore": 1, "num_healthy_workers": 2, "trial_id": "09c8ad76"}

以及一个用于可视化训练过程的TensorBoard文件。

rllib train命令有许多选项,可自行查看

rllib train --help

最重要的选项是使用--env选择环境(任何gym的环境以及用户自定义gym环境),以及使用--run选择算法(可用选项包括SAC,PPO,PG,A2C,A3C,IMPALA,ES,DDPG,DQN,MARWIL,APEX,APEX_DDPG)。

评估训练策略

为了保存checkpoints,当运行rilib train时设置--checkpoint-freq(两次保存之间的训练迭代次数)

评估以前训练得到的DQN策略:

rllib rollout 
    ~/ray_results/default/DQN_CartPole-vo_0upjmdgr0/checkpoint_1/checkpoint-1 
    --run DQN --env CartPole-vo --steps 10000

rollout.py将从位于~/ray_results/default/DQN_CartPole-vo_0upjmdgr0/checkpoint_1/checkpoint-1的策略重建DQN网络并渲染。

配置

指定参数

除了一堆common超参,每个算法都有特定的超参数,可以通过--config来设置。

如下我们指定A2C使用8个worker,

rllib train --env=PongDeterministic-v4 --run=A2C --config '{"num_workers": 8}'

指定资源

对大多数算法,可通过设置num_workers来指定并行程度。gpu资源可通过num_gpus选项设置。同样分配到worker的资源可通过num_cpus_per_worker,num_gpus_per_worker和custom_resources_per_worker来设置。GPU的数量可以是小数以分配GPU的一部分。

9785fc882339099f1edcba04ee609a11.png

Common参数

COMMON_CONFIG = {
    # === 用于调试 ===
    # 是否向log文件夹写入episode状态和视频
    "monitor": False,

    # 为agnet和workers设置ray.rllib.*的log等级
    # 应该为DEBUG,INFO,WARN,ERROR其中之一。 DEBUG 等级将会
    # 定期打印内部数据流的相关信息 (这也是INFO等级在一开始会打印的).
    "log_level": "INFO",

    # 训练不同阶段的回调函数。这些函数将会把单一的info作为参数,对于episode回调,我们可更新
    # episode对象的自定义度量字典,进而将自定义的度量指标能够附加在episode上,你还能改变回
    # 调中传入的批处理数据
    "callbacks": {
        "on_episode_start": None,     # arg: {"env": .., "episode": ...}
        "on_episode_step": None,      # arg: {"env": .., "episode": ...}
        "on_episode_end": None,       # arg: {"env": .., "episode": ...}
        "on_sample_end": None,        # arg: {"samples": .., "worker": ...}
        "on_train_result": None,      # arg: {"trainer": ..., "result": ...}
        "on_postprocess_traj": None,  # arg: {
                                      #   "agent_id": ..., "episode": ...,
                                      #   "pre_batch": (before processing),
                                      #   "post_batch": (after processing),
                                      #   "all_pre_batches": (other agent ids),
                                      # }
    },

    # 如果一个worker失败,是否继续
    "ignore_worker_failures": False,

    # log系统资源利情况
    "log_sys_usage": True,

    # 开启TF eager
    "eager": False,

    # === 策略 ===
    # 传入模型的参数,model/catalog.py中说明了全部参数
    "model": MODEL_DEFAULTS,

    # 传入优化器的参数. 随优化器而边
    "optimizer": {},

    # === 环境 ===
    # MDP折扣因子
    "gamma": 0.99,

    # 一个episode的最大步数。默认为gym环境的env.spec.max_episode_steps。
    "horizon": None,

    # 计算reward但是当步数达到horizon的时候不reset环境,这使得我们可以做value estimation
    # 而且可以将RNN状态在多个episode之间扩展。这个参数当horizon不为无穷时才有用。
    "soft_horizon": False,

    # 在episode结束的时候不设置done. 注意如果soft_horizon=True,你还是要设置done的,除非
    # 你的环境可以持续运行而不用重设
    "no_done_at_end": False,

    # 传给env creator的参数
    "env_config": {},

    # 环境的名字
    "env": None,

    # 是否在后处理时进行reward截断,设置为None则只对Atari环境做reward clip
    "clip_rewards": None,

    # 是否将动作截断在定义的动作空间高低区间上
    "clip_actions": True,

    # 是否默认使用rllib或者deepmind的预处理
    "preprocessor_pref": "deepmind",

    # 默认的学习率
    "lr": 0.0001,

    # === 评估 ===
    # 每 `evaluation_interval` 个训练迭代次数进行评估。
    # 评估的信息包含在“evaluation”度量键中
    # 当前评估不支持并行
    # Apex的度量只对其中一个worker进行。
    "evaluation_interval": None,

    # 每次评估运行的episode数量
    "evaluation_num_episodes": 10,

    # 要传给评估worker的其他参数
    # 典型的用法是传入用于评估的env creator的参数
    # 以及通过计算确定性动作关闭探索
    # TODO(kismuz): implement determ. actions and include relevant keys hints
    "evaluation_config": {},

    # === 资源 ===
    # 用于并行的actor个数
    "num_workers": 2,

    # 分配给训练过程的GPU资源. 不是所有算法都能利用GPU的,可以是小数(如0.3)
    "num_gpus": 0,

    # 分配给每个worker的CPU数量
    "num_cpus_per_worker": 1,

    # 分配给每个worker的GPU数量
    "num_gpus_per_worker": 0,

    # 分配给每个worker的自定义资源
    "custom_resources_per_worker": {},

    # 分配给trainer的CPU数量。注意:只有大那该在Tune中运行时才有效
    "num_cpus_for_driver": 1,

    # === 内存配额 ===
    # 可通过设置这些配额来告诉ray为你的训练保留这些内存,这保证了顺利的运行,
    # 代价是如果你的工作负荷超过配额就会失败

    # 为训练进程保留的堆内存(0代表无限)
    # 这可以很大如果你用大的batch,replay buffer等
    "memory": 0,

    # 为训练进程保留的对象存储空间. Being large
    # 足够容纳几份模型权重的拷贝即可
    # 默认开启,因为模型一般都很小.
    "object_store_memory": 0,

    # 为每个worker保留的堆内存
    # 一般来说小一点就好,除非你的环境很占内存
    "memory_per_worker": 0,

    # 为每个worker保留的对象存储空间
    # 大到一次容纳几个sample batch就足够
    # 默认开启,因为一般超不过200M
    "object_store_memory_per_worker": 0,

    # === 执行 ===
    # 每个worker的环境数量
    "num_envs_per_worker": 1,

    # 默认sample batch大小. 这样大小的batch不断从workers收集
    # 直到满足train_batch_size,如果一个worker用多个环境
    # 需要乘一个num_envs_per_worker
    "sample_batch_size": 200,

    # 用于训练的batch size, 应该 >= sample_batch_size.
    # Samples batches将会级联成这个大小用于训练
    "train_batch_size": 200,

    # 是否展开 "complete_episodes" or "truncate_episodes"
    "batch_mode": "truncate_episodes",

    # 使用后台线程用于采样 (因为不同步,轻微off-policy, 不建议打开
    # 除非你的环境要求)
    "sample_async": False,

    # 逐元素的observation过滤器, "NoFilter" 或者 "MeanStdFilter"
    "observation_filter": "NoFilter",

    # 是否同步remote过滤器的数据.
    "synchronize_filters": True,

    # 默认配置单进程tf op
    "tf_session_args": {
        # note: overriden by `local_tf_session_args`
        "intra_op_parallelism_threads": 2,
        "inter_op_parallelism_threads": 2,
        "gpu_options": {
            "allow_growth": True,
        },
        "log_device_placement": False,
        "device_count": {
            "CPU": 1
        },
        "allow_soft_placement": True,  # required by PPO multi-gpu
    },

    # 过载local worker的tf session参数
    "local_tf_session_args": {
        # 默认允许更高程度的并行,但是有限制
        # 因为那会造成多个并发dirver的冲突
        "intra_op_parallelism_threads": 8,
        "inter_op_parallelism_threads": 8,
    },

    # 是否用LZ4压缩单个observation
    "compress_observations": False,

    # 等待metric batches的最大时间(s). 没有按时返回的数据将在下一轮迭代中收集
    "collect_metrics_timeout": 180,

    # 在这样数量的episode下做度量平滑
    "metrics_smoothing_episodes": 100,

    # 如果num_envs_per_worker > 1, 是否在remote进程中创建这些env而不是在worker中
    # 这增加了通信开支, 但如果你的环境用很多时间step/reset(如星际争霸),这就很合理
    # 谨慎使用,overheads很重要
    "remote_worker_envs": False,

    # 和环境交互获取batch时remote worker的等待时间
    # 0 (当至少一个环境准备好后继续) 是一个合理的选择,
    # 但最优值需要测量环境的step/reset,以及model推断时间获得
    "remote_env_batch_wait_ms": 0,

    # 每次迭代的最少时间
    "min_iter_time_s": 0,

    # 每次train call最小的环境的步数
    # 这个值不影响训练效果,只影响每次迭代的长度
    "timesteps_per_iteration": 0,

    # 这个参数和 worker_index, 用来设置每个worker的随机种子
    # 这样相同的配置下就会有相同的结果
    # 这使得实验可以复现
    "seed": None,

    # === 离线数据集 ===
    # 用于指定如何产生经验:
    #  - "sampler": 通过在线仿真产生经验 (默认)
    #  - 一个局部路径或者全局文件表达形式 (如, "/tmp/*.json")
    #  - 文件路径或url的列表 (如, ["/tmp/1.json", "s3://bucket/2.json"])
    #  - 一个使用字符串为键和采样概率为值的字典 (如,
    #    {"sampler": 0.4, "/tmp/*.json": 0.4, "s3://bucket/expert.json": 0.2}).
    #  - 一个返回rllib.offline.InputReader的函数
    "input": "sampler",

    # 用于指定如何评估当前策略. 仅当读取离线经验时有效
    # 可用选项:
    #  - "wis": 加权重要性采样估计.
    #  - "is": 重要性采样估计.
    #  - "simulation": 后台运行环境,但仅用于评估不用于学习
    "input_evaluation": ["is", "wis"],

    # 是否在离线输入的轨迹片段上运行后处理trajectory()
    # 注意后处理将用当前策略而不是行为策略,对于on-policy算法这是不行的
    "postprocess_inputs": False,

    # 如果设置为正数, 将会通过一个这样数量batch的滑窗buffer将输入batch打乱
    # 如果输入数据顺序不够随机,就使用这个选项
    # 直到这个buffer填满,才会进行输入
    "shuffle_buffer_size": 0,

    # 指定经验保存的地方:
    #  - None: 不保存任何经验
    #  - "logdir":保存在agent的log目录下
    #  - 或者自定义任何路径/url (如, "s3://bucket/")
    #  - 一个返回rllib.offline.OutputWriter的函数
    "output": None,

    # 指定压缩为LZ4的sample batch columns
    "output_compress_columns": ["obs", "new_obs"],

    # 最大输出文件大小
    "output_max_file_size": 64 * 1024 * 1024,

    # === 多智能体 ===
    "multiagent": {
        # 从策略id到元祖 (policy_cls, obs_space,
        # act_space, config)的映射. See rollout_worker.py for more info.
        "policies": {},
        # 从agent id到policy id
        "policy_mapping_fn": None,
        # 有选择的选择要训练的策略
        "policies_to_train": None,
    },
}

Tuned例子

rllib train -f /path/to/tuned/example.yaml

Python API

python api提供了必要的灵活性,他可以用来自定义环境,预处理器,以及模型。

基本例子

import 
注意:建议使用Tune运行rllib trainer,这样可以使得实验管理更简单,并且可以可视化训练过程。 只需要在实验config中设置"run": ALG_NAME, "env": ENV_NAME

所有RLlib trainer都和Tune API兼容,如下的代码展示了一个简单的ppo超参数sweep。

import ray
from ray import tune

ray.init()
tune.run(
    "PPO",
    stop={"episode_reward_mean": 200},
    config={
        "env": "CartPole-v0",
        "num_gpus": 0,
        "num_workers": 1,
        "lr": tune.grid_search([0.01, 0.001, 0.0001]),
        "eager": False,
    },
)

Tune将会并行的在集群上训练.

== Status ==
Using FIFO scheduling algorithm.
Resources requested: 2/12 CPUs, 0/1 GPUs
Memory usage on this node: 5.1/33.3 GB
Result logdir: /home/yang/ray_results/PPO
Number of trials: 3 ({'TERMINATED': 2, 'RUNNING': 1})
RUNNING trials:
- PPO_CartPole-v0_1_lr=0.001: RUNNING, [2 CPUs, 0 GPUs], [pid=4478], 173 s, 39 iter, 156000 ts, 194 rew
TERMINATED trials:
- PPO_CartPole-v0_0_lr=0.01: TERMINATED, [2 CPUs, 0 GPUs], [pid=4482], 120 s, 24 iter, 96000 ts, 200 rew
- PPO_CartPole-v0_2_lr=0.0001: TERMINATED, [2 CPUs, 0 GPUs], [pid=4476], 70 s, 13 iter, 52000 ts, 200 rew

自定义训练工作流

默认的,Tune会在每一次迭代调用trainer上的train()并且报告新的训练结果。但有时我们需要自定义训练流。Tune也支持自定义训练函数,主要有两个API,一个python类API,一个python函数API。对更加细化的训练控制,就可以直接用RLlib的底层API(如policy,optimizer,evaluator等)来写。

"""Example of a custom training workflow. Run this for a demo.
This example shows:
  - using Tune trainable functions to implement custom training workflows
You can visualize experiment results in ~/ray_results using TensorBoard.
"""

from __future__ import absolute_import
from __future__ import division
from __future__ import print_function

import ray
from ray import tune
from ray.rllib.agents.ppo import PPOTrainer


def my_train_fn(config, reporter):
    # Train for 100 iterations with high LR
    agent1 = PPOTrainer(env="CartPole-v0", config=config)
    for _ in range(10):
        result = agent1.train()
        result["phase"] = 1
        reporter(**result)
        phase1_time = result["timesteps_total"]
    state = agent1.save()
    agent1.stop()

    # Train for 100 iterations with low LR
    config["lr"] = 0.0001
    agent2 = PPOTrainer(env="CartPole-v0", config=config)
    agent2.restore(state)
    for _ in range(10):
        result = agent2.train()
        result["phase"] = 2
        result["timesteps_total"] += phase1_time  # keep time moving forward
        reporter(**result)
    agent2.stop()


if __name__ == "__main__":
    ray.init()
    config = {
        "lr": 0.01,
        "num_workers": 0,
    }
    resources = PPOTrainer.default_resource_request(config).to_json()
    tune.run(my_train_fn, resources_per_trial=resources, config=config)

获取Policy状态

我们一般需要获取trainer的内部状态,如需要设置或获取内部权重。在RLlib中,trainer的state是在rollout workers之间复制存在的。你可以在调用train()方法的中间通过调用trainer.workers.foreach_worker()或者trainer.workers.foreach_worker_with_index()来获取和更新这些状态。这些方法的参数是一个用于worker的lambda函数,这个函数可以返回值,最后将以列表的形式返回。

也可以不用拿每个worker的状态而只获取其中一个主要的copy,trainer.get_policy()或者trainer.workers.local_worker()。

# 获取本地policy权重
trainer.get_policy().get_weights()

# 同上
trainer.workers.local_worker().policy_map["default_policy"].get_weights()

# 获取每个worker的权重,包括remote的replicas
trainer.workers.foreach_worker(lambda ev: ev.get_policy().get_weights())

# 同上
trainer.workers.foreach_worker_with_index(lambda ev, i: ev.get_policy().get_weights())

全局统筹

有时需要协调不同进程中的代码,比如我们有时需要维持一个变量的全局平均,或者集中控制一个policy的超参数。Ray通过named actor这个东西来实现。举个例子,比如我们现在需要维持一个全局计数器,这个计数器通过环境递增,并定期从驱动程序中读取。

from ray.experimental import named_actors

@ray.remote
class Counter:
   def __init__(self):
      self.count = 0
   def inc(self, n):
      self.count += n
   def get(self):
      return self.count

# on the driver
counter = Counter.remote()
named_actors.register_actor("global_counter", counter)
print(ray.get(counter.get.remote()))  # get the latest count

# in your envs
counter = named_actors.get_actor("global_counter")
counter.inc.remote(1)  # async call to increment the global count

Ray的actor有着很强的灵活性,它能够实现如ps和allreduce这样的通信模式。

回调和自定义度量

可以自定义用于policy evaluation过程的回调函数。这些回调函数将当前episode的状态的字典作为参数。自定义的状态量可以存储在info["episode"].user_data字典中,自定义的整数度量可以存储在info["episode"].custom_metrics字典中。这些自定义的度量将会作为训练结果的一部分。下列代码从环境中log了自定义的度量。

def on_episode_start(info):
    print(info.keys())  # -> "env", 'episode"
    episode = info["episode"]
    print("episode {} started".format(episode.episode_id))
    episode.user_data["pole_angles"] = []

def on_episode_step(info):
    episode = info["episode"]
    pole_angle = abs(episode.last_observation_for()[2])
    episode.user_data["pole_angles"].append(pole_angle)

def on_episode_end(info):
    episode = info["episode"]
    pole_angle = np.mean(episode.user_data["pole_angles"])
    print("episode {} ended with length {} and pole angles {}".format(
        episode.episode_id, episode.length, pole_angle))
    episode.custom_metrics["pole_angle"] = pole_angle

def on_train_result(info):
    print("trainer.train() result: {} -> {} episodes".format(
        info["trainer"].__name__, info["result"]["episodes_this_iter"]))

ray.init()
analysis = tune.run(
    "PG",
    config={
        "env": "CartPole-v0",
        "callbacks": {
            "on_episode_start": tune.function(on_episode_start),
            "on_episode_step": tune.function(on_episode_step),
            "on_episode_end": tune.function(on_episode_end),
            "on_train_result": tune.function(on_train_result),
        },
    },
)

自定义的度量同样可以在tensorboard中可视化

2478146decc0627154c96a7a49c41242.png

例子:课程学习

来看使用上述API实现课程学习的两种方式。在课程学习中,agent的任务随着学习过程不断调整,假设我们的环境类中有set_phase()方法,其可以随时间调节任务难度。

方法一:使用Trainer API在train()之间更新环境,以下例子展示了trainer在Tune函数中的运行。

import ray
from ray import tune
from ray.rllib.agents.ppo import PPOTrainer

def train(config, reporter):
    trainer = PPOTrainer(config=config, env=YourEnv)
    while True:
        result = trainer.train()
        reporter(**result)
        if result["episode_reward_mean"] > 200:
            phase = 2
        elif result["episode_reward_mean"] > 100:
            phase = 1
        else:
            phase = 0
        trainer.workers.foreach_worker(
            lambda ev: ev.foreach_env(
                lambda env: env.set_phase(phase)))

ray.init()
tune.run(
    train,
    config={
        "num_gpus": 0,
        "num_workers": 2,
    },
    resources_per_trial={
        "cpu": 1,
        "gpu": lambda spec: spec.config.num_gpus,
        "extra_cpu": lambda spec: spec.config.num_workers,
    },
)

方法二,使用回调函数

import ray
from ray import tune

def on_train_result(info):
    result = info["result"]
    if result["episode_reward_mean"] > 200:
        phase = 2
    elif result["episode_reward_mean"] > 100:
        phase = 1
    else:
        phase = 0
    trainer = info["trainer"]
    trainer.workers.foreach_worker(
        lambda ev: ev.foreach_env(
            lambda env: env.set_phase(phase)))

ray.init()
tune.run(
    "PPO",
    config={
        "env": YourEnv,
        "callbacks": {
            "on_train_result": tune.function(on_train_result),
        },
    },
)

调试

Gym Monitor

rllib train --env=PongDeterministic-v4 
    --run=A2C --config '{"num_workers": 2, "monitor": true}'

# videos will be saved in the ~/ray_results/<experiment> dir, for example
openaigym.video.0.31401.video000000.meta.json
openaigym.video.0.31401.video000000.mp4
openaigym.video.0.31403.video000000.meta.json
openaigym.video.0.31403.video000000.mp4

Tensorflow eager

使用build_tf_policy构建的策略可以通过设置"eager": True或者使用rllib train --eager使用eager模式运行。

Eager模式更方便调试,因为可以使用print来打印出tensor的值。

Episode Traces

可通过数据输出API保存episode信息用于调试,如下代码会将episode信息存入/tmp/debug

rllib train --run=PPO --env=CartPole-v0 
    --config='{"output": "/tmp/debug", "output_compress_columns": []}'

# episode traces will be saved in /tmp/debug, for example
output-2019-02-23_12-02-03_worker-2_0.json
output-2019-02-23_12-02-04_worker-1_0.json

Log verbosity

可以通过"log_level"控制训练log记录等级。 有INFO DEBUG WARN ERROR几种选择,

rllib train --env=PongDeterministic-v4 
    --run=A2C --config '{"num_workers": 2, "log_level": "DEBUG"}'

REST API

在有些情况下(如与一个外部simulator或者生产环境交互时),不适合用RLlib包裹这个simulator,而要通过RLlib的外部agent接口。

f9ed0e2d2f6e8f40d55584a2a596891b.png

03ffbfef4d4207004e3c720b6888a517.png

例子

>>> class CartpoleServing(ExternalEnv):
       def __init__(self):
           ExternalEnv.__init__(
               self, spaces.Discrete(2),
               spaces.Box(
                   low=-10,
                   high=10,
                   shape=(4,),
                   dtype=np.float32))
       def run(self):
           server = PolicyServer(self, "localhost", 8900)
           server.serve_forever()
>>> register_env("srv", lambda _: CartpoleServing())
>>> pg = PGTrainer(env="srv", config={"num_workers": 0})
>>> while True:
        pg.train()
>>> client = PolicyClient("localhost:8900")
>>> eps_id = client.start_episode()
>>> action = client.get_action(eps_id, obs)
>>> ...
>>> client.log_returns(eps_id, reward)
>>> ...
>>> client.log_returns(eps_id, reward)

完整client例子

完整server例子

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值