금융 트레이딩 강화학습을 위한 보상함수 아이디어들
2024. 11. 8. 19:51ㆍ금융공학/딥러닝

강화학습을 금융 트레이딩에 적용할 때 포트폴리오 수익률 외에도 다양한 보상 함수 설계가 가능합니다. 잘 설계된 보상 함수는 에이전트가 원하는 행동을 학습하게끔 유도하는 역할을 하며, 특히 수익률뿐만 아니라 리스크 관리와 안정적인 성과를 동시에 고려하도록 설계할 수 있습니다. 다음은 다양한 보상 함수 설계 방법과 그 계산 사례들입니다.
1. 수익률과 최대 하락폭(Drawdown) 고려
- 목표: 수익률을 최적화하되, 최대 하락폭을 줄이는 방향으로 학습.
- 설명: 포트폴리오의 최대 하락폭을 줄이는 방향으로 에이전트를 유도하여 리스크 관리도 함께 학습할 수 있습니다.\
def reward_with_drawdown(history):
current_value = history["portfolio_valuation"][-1]
prev_value = history["portfolio_valuation"][-2]
return_ratio = np.log(current_value / prev_value)
max_value = np.max(history["portfolio_valuation"])
drawdown = (max_value - current_value) / max_value
# 수익률 - 하락폭 페널티 (하락폭이 크면 보상 감소)
return return_ratio - drawdown
2. 변동성 조절 기반 보상
- 목표: 높은 수익률을 목표로 하되, 변동성을 줄여 안정적인 수익을 추구.
- 설명: 수익률이 높더라도 변동성이 크면 예측이 어려워지므로, 변동성이 큰 구간에서는 보상을 낮춰 변동성을 억제합니다.
def reward_with_volatility(history):
current_value = history["portfolio_valuation"][-1]
prev_value = history["portfolio_valuation"][-2]
return_ratio = np.log(current_value / prev_value)
# 최근 N 기간 동안의 변동성 계산
recent_returns = np.diff(np.log(history["portfolio_valuation"][-20:]))
volatility = np.std(recent_returns)
# 수익률 - 변동성 페널티 (변동성이 크면 보상 감소)
return return_ratio - volatility
3. 거래 비용을 고려한 순수익 보상
- 목표: 실제 수익률에서 거래 비용을 차감하여 과도한 거래를 억제.
- 설명: 거래가 빈번해질수록 수익이 거래 비용으로 감소하므로, 거래 비용을 고려하여 보상을 계산하면 과도한 거래를 방지할 수 있습니다.
def reward_with_transaction_cost(history, transaction_cost_rate=0.001):
current_value = history["portfolio_valuation"][-1]
prev_value = history["portfolio_valuation"][-2]
return_ratio = np.log(current_value / prev_value)
# 거래 발생 시 거래 비용 차감
position_changes = np.sum(np.abs(np.diff(history["position"])))
transaction_cost = transaction_cost_rate * position_changes
return return_ratio - transaction_cost
4. 샤프 비율(Sharpe Ratio) 기반 보상
- 목표: 위험 대비 수익률을 극대화.
- 설명: 샤프 비율은 수익률을 변동성으로 나눈 값으로, 위험 대비 수익률을 나타냅니다. 높은 샤프 비율은 안정적인 수익성을 나타내므로, 이를 통해 학습 방향을 설정할 수 있습니다.
def reward_with_sharpe_ratio(history):
returns = np.diff(np.log(history["portfolio_valuation"]))
avg_return = np.mean(returns)
volatility = np.std(returns)
sharpe_ratio = avg_return / (volatility + 1e-8) # 분모가 0이 되는 것을 방지
return sharpe_ratio
5. 칼마 비율(Calmar Ratio) 기반 보상
- 목표: 최대 하락폭 대비 수익률 최적화.
- 설명: 칼마 비율은 연간 수익률을 최대 하락폭으로 나눈 값으로, 위험 관리가 중요한 환경에서 유리합니다.
def reward_with_calmar_ratio(history):
returns = np.diff(np.log(history["portfolio_valuation"]))
avg_return = np.mean(returns)
max_value = np.max(history["portfolio_valuation"])
max_drawdown = (max_value - history["portfolio_valuation"][-1]) / max_value
calmar_ratio = avg_return / (max_drawdown + 1e-8) # 분모가 0이 되는 것을 방지
return calmar_ratio
6. 포트폴리오 회전율(Turnover)을 고려한 보상
- 목표: 자산 비율의 잦은 변동을 억제하여 안정적인 트레이딩 유도.
- 설명: 포트폴리오 회전율이 높으면 과도한 거래가 발생하므로, 이를 줄이기 위해 자산 비율 변화에 페널티를 부여합니다.
def reward_with_turnover_penalty(history, turnover_penalty=0.005):
current_value = history["portfolio_valuation"][-1]
prev_value = history["portfolio_valuation"][-2]
return_ratio = np.log(current_value / prev_value)
# 포트폴리오 회전율 계산
turnover = np.sum(np.abs(np.diff(history["position"]))) / len(history["position"])
# 회전율에 페널티 부여
return return_ratio - turnover_penalty * turnover
7. 정확한 예측력 보상
- 목표: 시장의 예측에 따라 트레이딩을 수행하도록 유도.
- 설명: 에이전트가 시장의 방향성을 맞춘 경우에만 보상을 주어 에이전트가 시장 예측 능력을 가지도록 학습합니다.
def reward_based_on_market_prediction(history):
current_value = history["portfolio_valuation"][-1]
prev_value = history["portfolio_valuation"][-2]
return_ratio = np.log(current_value / prev_value)
# 시장 방향성과 트레이딩 방향성이 일치할 때 보상
market_direction = np.sign(history["market_price"][-1] - history["market_price"][-2])
trade_direction = np.sign(history["position"][-1])
prediction_reward = return_ratio if market_direction == trade_direction else -abs(return_ratio)
return prediction_reward
8. 포트폴리오 위험 허용 한도 내에서 수익 극대화
- 목표: 특정 위험 한도 내에서 수익을 최적화.
- 설명: 위험을 초과하면 페널티를 부여하여 위험 한도를 유지하면서 수익을 극대화하도록 유도합니다.
def reward_with_risk_threshold(history, risk_threshold=0.02):
current_value = history["portfolio_valuation"][-1]
prev_value = history["portfolio_valuation"][-2]
return_ratio = np.log(current_value / prev_value)
# 특정 위험 허용 한도 초과 시 페널티
risk = np.std(np.diff(np.log(history["portfolio_valuation"][-20:])))
penalty = max(0, risk - risk_threshold)
return return_ratio - penalty
9. 통합
다양한 요소를 함께 고려하여 수익률, 리스크, 안정성을 조화롭게 최적화하는 보상 함수를 만들어 보겠습니다. 이 보상 함수는 다음과 같은 요소들을 조합하여 구성됩니다:
- 수익률: 전체적인 수익률을 고려하되, 다른 요소들과의 균형을 유지하도록 설정합니다.
- 최대 하락폭(Drawdown): 포트폴리오가 큰 손실을 입지 않도록 최대 하락폭에 페널티를 부여합니다.
- 변동성: 변동성이 큰 트레이딩은 위험하므로 변동성을 고려해 안정적인 성과를 유도합니다.
- 거래 비용: 과도한 거래를 억제하여 거래 비용을 절감합니다.
- 샤프 비율: 변동성 대비 수익률을 측정하여 리스크 대비 수익이 높아지도록 유도합니다.
- 포트폴리오 회전율: 잦은 포트폴리오 변경을 방지합니다.
def balanced_reward_function(history, transaction_cost_rate=0.001, turnover_penalty=0.005, risk_threshold=0.02):
"""
다양한 리스크 관리와 수익 요소를 고려한 종합적인 보상 함수.
Parameters:
- history: 트레이딩 환경에서 제공되는 포트폴리오 및 시장 정보 기록.
- transaction_cost_rate: 거래 발생 시 수익에서 차감할 거래 비용 비율.
- turnover_penalty: 포트폴리오 회전율에 부과할 페널티 비율.
- risk_threshold: 허용할 수 있는 최대 리스크 (변동성 기준).
Returns:
- 종합 보상 점수 (float)
"""
# 수익률 계산 (log 수익률)
current_value = history["portfolio_valuation"][-1]
prev_value = history["portfolio_valuation"][-2]
return_ratio = np.log(current_value / prev_value)
# 최대 하락폭 계산
max_value = np.max(history["portfolio_valuation"])
drawdown = (max_value - current_value) / max_value
# 최근 N 기간 동안의 변동성 계산
recent_returns = np.diff(np.log(history["portfolio_valuation"][-20:]))
volatility = np.std(recent_returns)
# 거래 비용 계산
position_changes = np.sum(np.abs(np.diff(history["position"])))
transaction_cost = transaction_cost_rate * position_changes
# 샤프 비율 계산
avg_return = np.mean(recent_returns)
sharpe_ratio = avg_return / (volatility + 1e-8) # 분모가 0이 되는 것을 방지
# 포트폴리오 회전율에 대한 페널티 계산
turnover = np.sum(np.abs(np.diff(history["position"]))) / len(history["position"])
# 리스크 초과 여부를 확인하고 페널티 추가
risk_penalty = max(0, volatility - risk_threshold)
# 보상 계산: 수익률, 샤프 비율을 더한 후 거래 비용, 변동성, 최대 하락폭 페널티 차감
reward = (
return_ratio # 수익률 보상
+ 0.5 * sharpe_ratio # 샤프 비율 보상 (가중치 0.5)
- 0.5 * drawdown # 최대 하락폭 페널티 (가중치 0.5)
- 0.5 * volatility # 변동성 페널티 (가중치 0.5)
- transaction_cost # 거래 비용 페널티
- turnover_penalty * turnover # 포트폴리오 회전율 페널티
- risk_penalty # 리스크 초과 페널티
)
return reward
'금융공학 > 딥러닝' 카테고리의 다른 글
| 데이터에 따른 활성함수의 선택과 전처리 중요성 (1) | 2024.11.23 |
|---|