154 lines
7.2 KiB
Markdown
154 lines
7.2 KiB
Markdown
---
|
||
ASMR++ 奖励计算完整分析
|
||
|
||
默认配置使用 reward_type: spatial_max + error_metric: maximum。整个奖励信号链分以下步骤:
|
||
|
||
Step 1: 误差估计 — 精细网格参考解
|
||
|
||
参考网格 (初始网格细化6次)
|
||
↓ FEM求解
|
||
参考解 u_ref (视为"真值")
|
||
↓
|
||
粗网格解 u_coarse 在每个积分点(参考网格元素中点)与 u_ref 比较
|
||
↓
|
||
绝对误差 |u_ref - u_coarse| per 积分点
|
||
↓ scatter_max per 粗元素
|
||
error_per_element: 每个粗网格元素内的最大误差 (num_elements, solution_dim)
|
||
|
||
用精细网格做数值积分 (error_integrator.py:86-169),支持三种积分方式:mean(积分平均值)、squared(积分平方误差)、maximum(元素内最大误差)。默认Poisson 是标量 PDE,solution_dim=1。
|
||
|
||
Step 2: spatial_max 奖励计算
|
||
|
||
核心代码在 mesh_refinement.py:657-714,以下是逐步推导:
|
||
|
||
奖励基准 (reward_per_agent_and_dim)
|
||
= previous_error_per_element ← 细分前该元素的误差
|
||
|
||
┌─────┬─────┐
|
||
│ │ │
|
||
├─────┼─────┤
|
||
│ │ │
|
||
└─────┴─────┘
|
||
|
||
父元素 i (error=0.8) 子元素: j1(0.3), j2(0.5), j3(0.6), j4(0.1)
|
||
↓ scatter_max per agent_mapping
|
||
max_mapped_error[i] = max(0.3, 0.5, 0.6, 0.1) = 0.6
|
||
↓
|
||
reward_raw[i] = 0.8 - 0.6 = +0.2 ✅ 误差最大的子元素也比父元素好
|
||
|
||
关键:spatial_max 只奖励"所有子元素误差都下降"的情况。如果有任一子元素误差仍等于原父元素误差,reward=0。
|
||
|
||
父元素 j (error=0.5) 子元素: k1(0.5), k2(0.1), k3(0.2), k4(0.05)
|
||
↓
|
||
max_mapped_error[j] = max(0.5, 0.1, 0.2, 0.05) = 0.5
|
||
↓
|
||
reward_raw[j] = 0.5 - 0.5 = 0 ❌ 有一个子元素仍未改善
|
||
|
||
对比 spatial (非 max) 模式:
|
||
|
||
reward_raw[i] = previous_error[i] - Σ_j φ_ij * error[j]
|
||
= 标量加法 (np.add.at) 把所有子元素误差从父元素误差中减去
|
||
这种模式下即使部分子元素没有改善,整体仍有正奖励。
|
||
|
||
Step 3: 归一化 + 降维到标量
|
||
|
||
# 除以初始网格的误差 → 把误差改善量归一化到 [0, ~1] 区间
|
||
reward_per_agent_and_dim = reward_per_agent_and_dim / initial_approximation_error
|
||
|
||
# 多维 PDE 降维: dot product with solution_dimension_weights
|
||
# Poisson 是标量PDE, weights=[1.0], 即恒等变换
|
||
reward_per_agent = project_to_scalar(reward_per_agent_and_dim)
|
||
# = np.dot(reward_per_agent_and_dim, [1.0]) = reward_per_agent_and_dim
|
||
|
||
Step 4: 元素惩罚 (Element Penalty)
|
||
|
||
# 统计每个父元素产生了多少子元素
|
||
element_counts = unique(agent_mapping, return_counts=True)[1] # 每个父元素→子元素的数量
|
||
element_counts = element_counts - 1 # 减1因为是"新增的"子元素数
|
||
|
||
# 默认 λ ~ 0.01 (loguniform 采样于 [1e-3, 1e-1])
|
||
element_penalty = λ * element_counts
|
||
|
||
┌──────────────────────────┬────────────────┬──────────────────┐
|
||
│ 场景 │ element_counts │ penalty (λ=0.01) │
|
||
├──────────────────────────┼────────────────┼──────────────────┤
|
||
│ 未细分元素 │ 0 │ 0 │
|
||
├──────────────────────────┼────────────────┼──────────────────┤
|
||
│ 分裂为 4 个子三角 │ 3 │ 0.03 │
|
||
├──────────────────────────┼────────────────┼──────────────────┤
|
||
│ 被波及细分 (Rivara 平滑) │ 1-3 │ 0.01-0.03 │
|
||
└──────────────────────────┴────────────────┴──────────────────┘
|
||
|
||
作用: 惩罚是正则化项,防止策略无节制细分所有元素。只在"误差改善 > 细分代价"时细分才有利。
|
||
|
||
Step 5: 元素上限惩罚 (Element Limit Penalty)
|
||
|
||
if num_elements > maximum_elements (20000):
|
||
element_limit_penalty = 1000 / previous_num_elements # ≈ 0.05~0.5 per agent
|
||
else:
|
||
element_limit_penalty = 0
|
||
|
||
Step 6: 最终每 Agent 奖励
|
||
|
||
r_i = error_improvement_i / initial_error
|
||
- λ * new_elements_created_by_i
|
||
- limit_penalty
|
||
|
||
形状为 (num_agents_t,) — 每个 agent(父元素)一个标量奖励。
|
||
|
||
Step 7: 奖励到 TD 误差 — 与论文公式 (3) 的对应
|
||
|
||
Buffer 存储:
|
||
r_i(s_t, a_t) ← 父元素 i 的奖励 (num_agents_t,)
|
||
V_i(s_t) ← 父元素 i 的价值 (num_agents_t,)
|
||
φ_ij = agent_mapping ← 子元素j → 父元素i 的映射
|
||
V_j(s_{t+1}) ← 子元素的价值 (num_agents_{t+1},)
|
||
|
||
GAE Delta 计算:
|
||
projected_V = scatter_sum(V_j(s_{t+1}), index=φ_ij) ← Σ_j φ_ij·V_j(s_{t+1})
|
||
δ_i = r_i + γ * projected_V_i - V_i(s_t)
|
||
|
||
对应论文 (3): δ_i^t = r(s^t, a^t)_i + γ·Σ_j φ_ij^t·V_j(s^{t+1}) - V_i(s^t)
|
||
|
||
Step 8: 混合奖励 (Mixed Return, global_weight=0.5)
|
||
|
||
在 MixedOnPolicyBuffer 中额外计算:
|
||
|
||
# 全局奖励 (均值)
|
||
r_global = mean(r_i) # 所有agent的平均奖励
|
||
|
||
# 全局价值 (均值)
|
||
V_global = mean(V_i) # 所有agent的平均价值
|
||
|
||
# 全局 GAE
|
||
δ_global = r_global + γ·V_global' - V_global
|
||
|
||
# 局部 GAE
|
||
δ_local_i = 上述 per-agent GAE
|
||
|
||
# 混合 Advantage
|
||
A_i = (1 - 0.5) * A_local_i + 0.5 * A_global
|
||
|
||
完整奖励流总结
|
||
|
||
FEM求解 → 逐元素误差估计 (±积分 vs 参考网格)
|
||
↓
|
||
spatial_max: error_before - max_error_of_children
|
||
↓
|
||
归一化 (/ initial_error)
|
||
↓
|
||
- λ * new_elements + limit_penalty
|
||
↓
|
||
r_i (per agent) ────────────→ 局部 GAE → A_local_i
|
||
│ ↓
|
||
└→ r_global = mean(r_i) → 全局 GAE → A_global
|
||
↓
|
||
A_i = 0.5·A_local_i + 0.5·A_global
|
||
↓
|
||
送入 PPO policy_loss
|
||
|
||
设计精巧之处:
|
||
1. 空间奖励 + agent_mapping:每个元素独立计算误差改善,通过 agent_mapping φ_ij 追踪父→子关系
|
||
2. spatial_max 语义:reward 表示"最差子元素的误差下降量"——驱动策略优先细分误差最大的区域
|
||
3. 元素惩罚:防止盲目细分,精确到每个 agent 独立计算代价
|
||
4. 混合奖励:局部信号指导细粒度决策 + 全局信号稳定整体训练 |