역 시뮬레이션 검증을 통한 해안 기후 회복력 계획을 위한 인간 정렬 Decision Transformers
요약
Decision Transformers를 활용하여 해안 기후 회복력 계획을 수립하고, 역 시뮬레이션 검증(inverse simulation verification)을 통해 모델의 결정 과정을 감사하는 새로운 프레임워크를 제안합니다. 이 방식은 기후 변화의 불확실성과 상충하는 인간의 선호도를 반영하면서도, 모델이 내린 결정의 타당성을 역방향 시뮬레이션으로 설명할 수 있게 합니다.
핵심 포인트
- Decision Transformers를 통해 강화학습 문제를 시퀀스 모델링으로 프레임화하여 다중 모드 보상 지형을 처리함
- 역 시뮬레이션 검증 기술을 도입하여 모델이 생성한 계획의 타당성을 '풀이 과정'처럼 검토 가능
- 전통적인 선형 계획법의 한계인 정적 확률 분포 가정과 상충하는 인간 선호도 문제를 해결
- 해수면 상승, 경제적 비용, 생태계 보존 등 다중 목적 최적화가 필요한 복잡한 기후 시나리오에 적용 가능
역 시뮬레이션 (inverse simulation) 검증을 통한 해안 기후 회복력 계획을 위한 인간 정렬 Decision Transformers
지난 여름, IPCC 보고서 더미와 해안 침수 모델을 면밀히 검토하던 중, 저는 AI 기반 기후 계획에 대한 저의 관점 전체를 바꾸어 놓은 깨달음을 얻었습니다. 저는 강화학습 (reinforcement learning)을 시퀀스 모델링 (sequence modeling)으로 프레임화하는 모델 클래스인 Decision Transformers를 실험하고 있었고, 이것이 해안 회복력을 위한 인간의 직관과 기계의 최적화 사이의 끊어진 연결 고리가 될 수 있음을 깨달았습니다. 하지만 문제가 있었습니다. 이러한 모델들은 종종 서류상으로는 훌륭해 보이지만, 현실이 훈련 데이터 (training data)와 달라질 때 처참하게 실패하는 계획을 생성한다는 점이었습니다. 그때부터 저는 모델이 자신의 결정으로부터 시뮬레이션을 역방향으로 실행함으로써 "풀이 과정을 보여주도록" 요구하는 기술인 역 시뮬레이션 검증 (inverse simulation verification)을 탐구하기 시작했습니다. 그 결과, 적응형 해안 방어 계획을 세울 뿐만 아니라 불확실성 속에서 왜 해당 계획이 타당한지를 설명하는 프레임워크가 탄생했습니다.
핵심 문제: 전통적인 계획이 실패하는 이유
해안 기후 회복력 계획은 이해관계가 매우 높고 다중 목적 최적화 (multi-objective optimization)가 필요한 문제입니다. 우리는 가속화되는 해수면 상승, 폭풍 해일, 인구 이동을 고려하는 동시에 경제적 비용, 생태계 보존, 사회적 형평성, 그리고 인프라의 견고함 사이의 균형을 맞춰야 합니다. 전통적인 접근 방식은 시나리오 분석 (예: "최악의 상황", "가장 가능성 높은 상황") 또는 선형 계획법 (linear programming)에 의존하지만, 이러한 방법들은 다음과 같은 한계가 있습니다:
- 정적 확률 분포 (stationary probability distributions)를 가정함 (기후는 정적이지 않음)
- 상충하는 인간의 선호도(예: "관광 보호" vs "습지 보존")를 처리하는 데 어려움을 겪음
- 계획이 새로운 충격에 진정으로 회복력이 있는지 검증할 메커니즘을 제공하지 않음
이 문제를 해결하기 위해 Decision Transformers를 조사하는 동안, 저는 이 모델들이 인간 결정의 오프라인 궤적 (offline trajectories)으로부터 학습하기 때문에 다중 모드 보상 지형 (multi-modal reward landscapes)을 자연스럽게 처리한다는 것을 발견했습니다. 하지만 진정한 돌파구는 우리가 역 시뮬레이션을 사용하여 해당 결정들을 감사 (audit)할 수 있다는 것을 깨달았을 때 찾아왔습니다.
기술적 배경: Decision Transformers와 역 시뮬레이션의 만남
Decision Transformers (DTs) 요약
Decision Transformer는 상태 (states), 행동 (actions), 그리고 보상 (rewards)의 전체 이력을 하나의 시퀀스 (sequence)로 취급합니다. 시간차 학습 (Temporal Difference Learning)을 통해 정책 (policy)을 학습하는 대신, 인과적 트랜스포머 (causal transformer)를 사용하여 과거의 문맥 (context)과 목표로 하는 잔여 보상 (return-to-go, RTG)을 조건으로 행동을 예측합니다. 형식적으로는 다음과 같습니다: 궤적 시퀀스 $\tau = (R_1, s_1, a_1, R_2, s_2, a_2, \dots)$가 주어졌을 때 (여기서 $R$은 누적 미래 보상 (return-to-go), $s$는 상태, $a$는 행동), 모델은 다음을 학습합니다: $p(a_t \mid s_t, R_t, s_{t-1}, a_{t-1}, R_{t-1}, \dots)$
이러한 프레임워크가 강력한 이유는 다음과 같습니다:
- 인간 계획가들로부터 얻은 대규모 오프라인 데이터셋 (offline datasets)을 활용할 수 있습니다.
- 지연된 보상 (delayed rewards)을 자연스럽게 처리합니다 (해안 방어 시설 구축에는 수십 년이 걸립니다).
- RTG를 통해 서로 다른 "야심의 수준 (levels of ambition)"을 조건으로 설정할 수 있습니다.
역 시뮬레이션 검증 (Inverse Simulation Verification, ISV)
ISV는 DT를 더욱 신뢰할 수 있게 만드는 방법을 탐구하는 과정에서 제가 개발한 기술입니다. 아이디어는 간단합니다. DT가 계획을 제안한 후, 미분 가능한 시뮬레이터 (differentiable simulator)를 종료 상태 (terminal state)로부터 역방향으로 실행하여, 제안된 행동들이 실제로 주장된 결과로 이어지는지 확인하는 것입니다. 형식적으로는 다음과 같습니다: 순방향 시뮬레이터 (forward simulator)를 $F(s_t, a_t) \to s_{t+1}$라고 합시다. 제안된 궤적 $(s_0, a_0, \dots, a_{t-1}, s_t)$가 주어졌을 때, 우리는 다음을 계산합니다: $\Delta = \sum |s_t - F(s_{t-1}, a_{t-1})|^2 + \lambda \cdot |s_0 - F^{-1}(s_1, a_0)|^2$ (여기서 $F^{-1}$은 학습된 역모델 (inverse model)입니다). 높은 $\Delta$ 값은 해당 계획이 시뮬레이터의 역학 (dynamics)과 일치하지 않음을 나타내며, 이는 비현실적인 가정이 포함되어 있다는 위험 신호 (red flag)입니다.
구현 세부 사항
제가 구축한 핵심 구현 내용을 살펴보겠습니다. 전체 코드베이스는 GitHub에 공개되어 있지만, 여기 주요 구성 요소들이 있습니다.
- 해안 환경 시뮬레이터
import jax.numpy as jnp
import flax.linen as nn
from typing import Tuple
class CoastalCellState:
""" 해안 구역의 상태를 나타냄 """
def __init__(self, elevation, wave_energy, defense_height, population, wetland_area):
self.elevation = elevation # 평균 해수면 기준 미터(m)
self.wave_energy = wave_energy
self.defense_height = defense_height
self.population = population
self.wetland_area = wetland_area
wave_energy = wave_energy # kW/m self . defense_height = defense_height # meters self . population = population # thousands self . wetland_area = wetland_area # hectares class CoastalDynamics ( nn . Module ): """ 해안 과정에 대한 미분 가능한 순방향 시뮬레이터 """ features : int = 128 @nn.compact def call ( self , state , action , sea_level_rise_rate ): # action: [해안 방벽 건설, 습지 복원, 인구 재배치, 아무것도 안 함] # 다음 상태 반환 # 행동 효과 처리 new_defense = state . defense_height + action [ 0 ] * 2.0 # 해안 방벽은 2m 추가됨 new_wetland = state . wetland_area + action [ 1 ] * 50.0 # 복원 # 기후 영향 (미분 가능) erosion_rate = 0.3 * jnp . tanh ( state . wave_energy / 100.0 ) new_elevation = state . elevation - sea_level_rise_rate * 0.1 - erosion_rate * 0.05 # 인구 역학 (수용 능력과 로지스틱 성장) capacity = 500 + new_wetland * 2.0 growth = 0.02 * state . population * ( 1 - state . p
shape [ 1 ] # 인간 선호도(human preferences)를 학습된 토큰으로 임베딩합니다. pref_embed = nn . Dense ( self . embed_dim )( human_prefs ) # [B, embed_dim] pref_embed = pref_embed [:, None , :] # [B, 1, embed_dim] # 위치 인코딩(Positional encoding) pos_embed = nn . Embed ( num_embeddings = 1024 , features = self . embed_dim )( timesteps ) # 상태(State), 행동(action), 보상 임베딩 state_embed = nn . Dense ( self . embed_dim )( states ) action_embed = nn . Dense ( self . embed_dim )( actions ) return_embed = nn . Dense ( self . embed_dim )( returns_to_go ) # 선호도 조건부 시퀀스에 연결(Concatenate) sequence = jnp . concatenate ([ state_embed + pos_embed + pref_embed , action_embed + pos_embed + pref_embed , return_embed + pos_embed + pref_embed ], axis = 1 ) # 인과 트랜스포머(Causal transformer) x = sequence for _ in range ( self . num_layers ): x = nn . SelfAttention ( num_heads = self . num_heads , causal_mask = True )( x ) x = nn . LayerNorm ()( x + sequence ) x = nn . Dense ( self . embed_dim )( x ) x = nn . gelu ( x ) x = nn . Dense ( self . embed_dim )( x ) x = nn . LayerNorm ()( x + sequence ) # 출력 행동 로짓(Output action logits) action_logits = nn . Dense ( 4 )( x [:, 1 :: 3 ]) # 4가지 행동 유형을 반환합니다. return action_logits
- 역 시뮬레이션 검증 모듈(Inverse Simulation Verification Module)
클래스 InverseVerifier ( nn . Module ):
""" 계획의 일관성(consistency)을 역방향 시뮬레이션을 통해 검증합니다."""
features : int = 64
@nn.compact
def call ( self , forward_dynamics , proposed_trajectory ):
""" proposed_trajectory: (state, action) 쌍 리스트를 받습니다.
반환값: consistency_score (값이 낮을수록 일관성이 높음)
"""
순방향 검증(Forward verification)
forward_errors = []
for t in range ( len ( proposed_trajectory ) - 1 ):
state_t , action_t = proposed_trajectory [ t ]
state_t1_pred = forward_dynamics ( state_t , action_t , sea_level_rise = 0.05 )
state_t1_actual = proposed_trajectory [ t + 1 ][ 0 ]
forward_errors . append ( jnp . mean (( state_t1_pred - state_t1_actual ) ** 2 ))
역방향 검증(Backward verification) (역 시뮬레이션)
inverse_model = nn . Dense ( self . features )( jnp .
concatenate ([ proposed_trajectory [ - 1 ][ 0 ], # 터미널 상태(terminal state) proposed_trajectory [ - 1 ][ 1 ] # 마지막 행동(last action) ])) inverse_model = nn.Dense(4)(inverse_model)# 역방향 예측된 행동(predict inverse action backward_errors = [] for t in range(len(proposed_trajectory) - 1, 0, -1): state_t, action_t = proposed_trajectory[t]state_t_minus1_pred = inverse_model(state_t, action_t)state_t_minus1_actual = proposed_trajectory[t-1][0]backward_errors.append(jnp.mean((state_t_minus1_pred - state_t_minus1_actual)**2))# 결합 일관성 점수(Combined consistency score)consistency = jnp.mean(jnp.array(forward_errors)) + 0.5 * jnp.mean(jnp.array(backward_errors))return consistency
4. 인간 피드백을 통한 학습 루프 (Training Loop with Human Feedback)
def train_with_human_alignment(dt_model, env, human_preference_dataset, num_epochs=100):
""" DT를 인간 선호도 레이블(human preference labels)을 사용하여 미세 조정(Fine-tune)합니다."""
optimizer = optax.adamw(learning_rate=3e-4, weight_decay=0.01)
for epoch in range(num_epochs):
인간 선호도 주석이 달린 궤적 배치 샘플링
batch = sample_batch(human_preference_dataset, batch_size=32)
def loss_fn(params):
순방향 전달(Forward pass) 행동 로짓 계산
action_logits = dt_model.apply(params, batch['states'], batch['actions'], batch['returns_to_go'], batch['timesteps'], batch['human_prefs'])
행동 예측 손실 (Action prediction loss)
action_loss = optax.softmax_cross_entropy(action_logits, batch['actions'])
역방향 검증 일관성 손실 (Inverse verification consistency loss)verifier = InverseVerifier()
consistency = verifier(env.forward_dynamics, list(zip(batch['states'], batch['actions'])))
인간 정렬 보상 (Human alignment reward) (선호도 모델에서 가져옴)
alignment_score = human_preference_model(batch['states'], batch['actions'])
total_loss = action_loss + 0.1 * consistency - 0.5 * alignment_score
return total_loss
grads = jax.grad(loss_fn)(dt_model.params)
dt_model.params = optimizer.update(grads, dt_model.
params) if epoch % 10 == 0: print(f" Epoch {epoch}: Loss = {loss_fn(dt_model.params):.4f}")
실제 응용 사례: 마이애미-데이드 카운티 (Miami-Dade County) 사례 연구
이 프레임워크를 학습하면서, 저는 마이애미-데이드 카운티의 2022년 기후 회복력 계획 (Climate Resilience Plan)에서 추출한 실제 데이터셋에 이를 적용해 보았습니다. 해당 데이터셋에는 15년간의 해안 관리 결정, 폭풍 해일 (storm surge) 기록, 그리고 인구 밀도 지도가 포함되어 있었습니다. 제가 발견한 결과는 다음과 같습니다:
인간 정렬 (Human-Aligned) DT 출력
서로 다른 인간 선호도 벡터 (human preference vectors)를 조건으로 설정했을 때, 모델은 극명하게 다른 계획들을 생성했습니다:
| 선호도 벡터 (Preference Vector) | 방파제 높이 (m) | 습지 복원 (ha) | 인구 이주 비용 ($B) | 일관성 점수 (Consistency Score) |
|---|---|---|---|---|
| 0.7, 0.1, 0.1, 0.1 | 4.2 | 120 | 5,000 | 2.3 |
| 0.1, 0.7, 0.1, 0.1 | 1.8 | 450 | 12,000 | 4.1 |
| 0.1, 0.1, 0.7, 0.1 | 3.5 | 200 | 2,000 | 3.8 |
| 0.1, 0.1, 0.1, 0.7 | 5.1 | 300 | 8,000 | 5.2 |
역 시뮬레이션 (inverse simulation)을 통해 얻은 일관성 점수를 분석한 결과, 생태적 계획이 가장 높은 일관성을 보였습니다. 이는 습지 복원이 자연스럽게 파동 에너지 (wave energy)를 감쇄시켜, 해수면 상승의 불확실성에 대해 해당 계획이 덜 민감하게 반응하기 때문입니다.
직면한 과제와 해결책
직면한 과제 1: 선호도 도출 (Preference Elicitation)의 모호성
실험 과정에서 저는 인간 계획가들이 자신의 선호도를 수치로 명확하게 표현하지 못하는 경우가 많다는 것을 발견했습니다. 저는 관찰된 계획 결정으로부터 선호도를 추론하는 선호도 학습 모듈 (preference learning module)을 구현함으로써 이 문제를 해결했습니다:
class PreferenceInference(nn.Module):
""" 관찰된 결정으로부터 인간의 선호도를 학습함 """
@nn.compact
def __call__(self, trajectory):
# 역강화학습 (Inverse Reinforcement Learning)을 사용하여 선호도 추론
state_features = nn.Dense(32)(trajectory['states'])
action_features = nn.Dense(32)(trajectory['actions'])
# 선형 보상 함수 (linear reward function) 학습
reward_weights = nn.Dense(4, use_bias=False)(jnp.concatenate([state_features, action_features], axis=-1))
# 선호도 벡터로 정규화
preferences = nn.
softmax(reward_weights, axis=-1) return preferences
도전 과제 2: 역 시뮬레이션 (Inverse Simulation)의 계산 비용
제안된 모든 계획에 대해 전체 역 시뮬레이션을 실행하는 것은 계산 비용 측면에서 매우 부담스러웠습니다. 저는 Decision Transformer (DT)의 어텐션 점수 (attention scores)를 통해 식별된 핵심 결정 지점만을 확인하는 확률적 검증 (stochastic verification) 접근 방식을 개발했습니다:
```python
def stochastic_inverse_verify(dt_model, plan, attention_scores, threshold=0.7):
""" 높은 어텐션이 부여된 결정 지점만 검증"""
critical_indices = jnp.where(attention_scores > threshold)[0]
# 검증을 위해 핵심 지점의 20%를 샘플링
sampled_indices = jnp.random.choice(
critical_indices,
size=int(0.2 * len(critical_indices)),
replace=False
)
consistency_scores = []
fo
AI 자동 생성 콘텐츠
본 콘텐츠는 Dev.to AI tag의 원문을 AI가 자동으로 요약·번역·분석한 것입니다. 원 저작권은 원저작자에게 있으며, 정확한 내용은 반드시 원문을 확인해 주세요.
원문 바로가기