引入专家约束
引入专家约束可以为模型的训练和推断提供专业领域知识支持,避免从数据中学习到的环境模型违背约束的知识,减少任务难度,并提高环境模型预测精度。
在冰箱温度控制任务中,存在一个专家先验,即冰箱功率增大会导致冰箱温度下降的负相关关系。将这个负相关关系作为一个专家约束,对模型的训练和推断可以提供专业领域知识的支持,有效地避免了从数据中学习到的环境模型与约束知识违背的情况。在模型中引入这个约束可以降低任务难度并提高预测精度,在实践中具有很高的应用价值。
REVIVE SDK支持以函数的形式引入专家约束。构建的方式类似于奖励函数,约束函数根据环境转移是否违背约束来给予一个奖励。
下面是一个为冰箱示例引入专家约束的示例,首先我们定义一个类似奖励函数的专家约束:
python
import torch
from copy import deepcopy
from typing import Dict
# Whether to normalize the computed reward values (default: False)
normalize = False
# Weight applied to the computed reward; this can be adjusted here or within the function below
weight = 1.0
# Configuring matching_nodes can help assign rules to specified matchers (optional)
matching_nodes = ["temperature", "action", "next_temperature"]
# The function name should be defined as get_reward
def get_reward(data: Dict[str, torch.Tensor], graph) -> torch.Tensor:
# Create a copy of the original data
noise_data = deepcopy(data)
# Add random noise to the 'action' node of the original data
noise_data["action"] += torch.randn_like(noise_data["action"]) * 0.1
# Compute the output of the 'next_temperature' node using the noisy data
node_name = "next_temperature"
if graph.get_node(node_name).node_type == 'network':
# Call the graph to compute the output of the network node
node_output = graph.compute_node(node_name, noise_data).mode
else:
# Call the graph to compute the output of the function node
node_output = graph.compute_node(node_name, current_batch)
# Compute the correlation between the changes in the 'action' node and the 'next_temperature' node
correlation = ((noise_data["action"] - data["action"]) * (node_output - data[node_name]))
# If a positive correlation exists, assign a reward of -0.2; otherwise, assign a reward of 0
reward = torch.where(
correlation > 0,
-0.2 * torch.ones_like(correlation[..., :1]),
torch.zeros_like(correlation[..., :1])
)
return reward
需要注意,在使用专家约束函数对数据进行处理时,通常会将多个数据按批量(batch)组织起来进行一次性运算处理。这种方式可以提高代码的运行效率。因此,在编写奖励函数时,需要注意保证函数能够处理与输入张量形状相对应的多维数据。此外,在计算专家约束函数输出时,我们通常会关注最后一维的特征维度。
为方便处理,专家函数的计算维度通常都设在了最后一维。因此,在使用数据时需要使用切片([..., n:m ]
)的方式获取数据的最后一维的特征,并对特征进行计算。而对应返回的reward应该是一个对应的Pytorch Tensor,batch维度保持和输入数据一致, 最后一维特征的维度应该是1。
通过-mrf参数引入专家约束函数进行环境训练的命令:
bash
python train.py \
-df test_data.npz \
-cf test.yaml \
-mrf data/test_rule.py \
-rf test_reward.py \
-vm once \
-pm once \
--run_id once