Workspace IndexMath › Day 36

Log Returns and Volatility (σ) TODO

Math · Day 36 / 52 · November — Probability, Statistics & Financial Math (Day 35-43)

Concept

Log return is defined as the natural logarithm of the ratio of consecutive prices, ln(P_t/P_{t-1}). Unlike simple returns, log returns add up over consecutive periods, which makes multi-period aggregation easy, treats gains and losses symmetrically, and is nearly identical to the simple return when the value itself is small. Volatility σ is the standard deviation of these returns; under the assumption that returns are independent and identically distributed, it scales with the square root of the time period, so short-interval volatility is converted to a longer horizon by multiplying by the square root of the number of periods. Real financial time series don't fully satisfy that assumption — they show fat tails and volatility clustering — which is why realized volatility computed from historical data differs from the implied volatility backed out of option prices. The choice of sample window length and observation frequency has a large effect on the estimate.

Risk limits, margin, and pricing models all rest on volatility figures, but mechanically applying square-root-of-time scaling systematically underestimates tail risk. Knowing which assumptions a given number rests on is the whole point.

Code & Formula

# Day 36 — 로그수익률·변동성(σ)
# 짧은 가격 시계열에서 로그수익률을 계산하고 표준편차(변동성)를 구한 뒤, 기간 환산을 보여준다.

import math

prices = [100.0, 101.5, 99.8, 102.3, 103.0, 101.0, 104.5, 103.8, 106.0, 105.2]

log_returns = [math.log(prices[i] / prices[i - 1]) for i in range(1, len(prices))]

n = len(log_returns)
mean_r = sum(log_returns) / n
variance = sum((r - mean_r) ** 2 for r in log_returns) / (n - 1)  # 표본분산 (n-1)
daily_vol = math.sqrt(variance)

print("가격:", prices)
print("\n일별 로그수익률:")
for i, r in enumerate(log_returns, start=1):
    print(f"  day {i}: {r:+.5f}")

print(f"\n평균 로그수익률 = {mean_r:.5f}")
print(f"일간 변동성(σ_daily) = {daily_vol:.5f}")

# 연환산: iid 가정 아래 변동성은 기간 수의 제곱근에 비례
trading_days = 252
annual_vol = daily_vol * math.sqrt(trading_days)
print(f"연환산 변동성(σ_annual, sqrt(252) 법칙) = {annual_vol:.5f} ({annual_vol*100:.2f}%)")

Exercise

Take a daily closing-price series for any asset, compute log returns, derive the standard deviation and its square-root-time-scaled value, then compare the frequency of extreme moves the normal-distribution assumption predicts against what actually occurred.

Practical Connection

Prediction-market prices are probabilities bounded between 0 and 1, so log returns don't apply directly, but converting to log-odds aligns with the way LMSR prices respond linearly to holdings — giving volatility analysis a natural coordinate system.

If you study this on a given day, add a note link and a ✅ to this line in the source curriculum (docs/knowledge/math-50-curriculum.md) and this spot will lead straight to the note body. You can also write directly on this page — but regenerating overwrites it, so it's safer to keep anything you want to save as markdown under docs/algorithms/.


한국어

로그수익률·변동성(σ) TODO

Math · Day 36 / 52 · 11월 — 확률·통계·금융수학 (Day 35–43)

개념

로그수익률은 연속된 가격의 비를 자연로그로 취한 값 ln(P_t/P_{t-1})로 정의된다. 단순수익률과 달리 기간을 이어 붙일 때 단순 덧셈이 되어 다기간 집계가 쉽고, 상승과 하락이 대칭적으로 표현되며 값이 작을 때는 단순수익률과 거의 같다. 변동성 σ는 이 수익률의 표준편차이며, 수익률이 독립동일분포라는 가정 아래에서는 기간 길이의 제곱근에 비례해 커지므로 짧은 주기 변동성에 기간 수의 제곱근을 곱해 환산한다. 실제 금융 시계열은 이 가정을 잘 만족하지 않아 두꺼운 꼬리와 변동성 군집이 나타나고, 그래서 과거 데이터로 계산한 실현 변동성과 옵션 가격에서 역산한 내재 변동성이 서로 다르다. 추정할 때는 표본 구간 길이와 관측 주기 선택이 결과를 크게 좌우한다.

리스크 한도, 마진, 가격 모델이 모두 변동성 수치 위에 서 있는데 제곱근 스케일링을 기계적으로 적용하면 꼬리 위험을 체계적으로 과소평가한다. 어떤 가정에서 나온 숫자인지 아는 것이 핵심이다.

코드 · 수식

# Day 36 — 로그수익률·변동성(σ)
# 짧은 가격 시계열에서 로그수익률을 계산하고 표준편차(변동성)를 구한 뒤, 기간 환산을 보여준다.

import math

prices = [100.0, 101.5, 99.8, 102.3, 103.0, 101.0, 104.5, 103.8, 106.0, 105.2]

log_returns = [math.log(prices[i] / prices[i - 1]) for i in range(1, len(prices))]

n = len(log_returns)
mean_r = sum(log_returns) / n
variance = sum((r - mean_r) ** 2 for r in log_returns) / (n - 1)  # 표본분산 (n-1)
daily_vol = math.sqrt(variance)

print("가격:", prices)
print("\n일별 로그수익률:")
for i, r in enumerate(log_returns, start=1):
    print(f"  day {i}: {r:+.5f}")

print(f"\n평균 로그수익률 = {mean_r:.5f}")
print(f"일간 변동성(σ_daily) = {daily_vol:.5f}")

# 연환산: iid 가정 아래 변동성은 기간 수의 제곱근에 비례
trading_days = 252
annual_vol = daily_vol * math.sqrt(trading_days)
print(f"연환산 변동성(σ_annual, sqrt(252) 법칙) = {annual_vol:.5f} ({annual_vol*100:.2f}%)")

연습

임의의 자산 일별 종가 시계열로 로그수익률을 계산해 표준편차와 제곱근 스케일 환산값을 구하고, 정규분포 가정에서 기대되는 극단값 빈도와 실제 빈도를 비교하라.

실무 · Verex 연결

예측시장 가격은 0과 1 사이의 확률이라 로그수익률을 그대로 쓰기 어렵지만, 로그 오즈로 변환하면 LMSR에서 가격이 보유량에 선형으로 반응하는 구조와 맞아떨어져 변동성 분석의 자연스러운 좌표가 된다.

공부한 날 원본 커리큘럼(docs/knowledge/math-50-curriculum.md)의 이 줄에 노트 링크와 ✅ 를 붙이면, 이 자리는 노트 본문으로 바로 이어집니다. 노트 없이 이 페이지에 바로 적어도 됩니다 — 다만 다시 생성하면 덮어쓰이므로, 남길 글은 docs/algorithms/ 의 마크다운으로 쓰는 편이 안전합니다.

← 35. 조건부확률·베이즈·기대값·정규분포37. 집중부등식(Chebyshev·Hoeffding, 12월 다리) →