W2 Homework W2 과제 워크북 0 / 100 점
📝 HOMEWORK
WEEK 2

기술적 지표 자동화
RSI · MA · Bollinger Bands

총점 100점 · 필수 60 + 심화 40
🎯 W2 학습 목표 복습

Code 노드에서 순수 JavaScript로 기술적 지표를 직접 구현. 외부 라이브러리 없이 RSI·이동평균·볼린저 밴드의 수학적 원리 체득.

🔧 핵심 개념
과거 30일 데이터
이동 윈도우 계산
매수/매도 시그널
⏱ 예상 시간
필수 4~5시간
심화 +3시간
📊 과제 배점표
과제 1
20
과제 2
20
과제 3
20
과제 4
20
과제 5
20
합계 100점 · 필수 60 + 심화 40
📍 빠른 이동
🔴 REQUIRED — 과제 1
RSI(14) 직접 구현 + 5종목 계산
배점 20

Code 노드에서 RSI(Relative Strength Index) 14일 기간을 직접 계산하는 함수를 작성하고, 관심 종목 5개에 적용합니다.

RSI 공식
RSI = 100 − (100 / (1 + RS))
RS = 평균 상승폭 / 평균 하락폭
필수 요구사항
  • Yahoo Finance에서 최근 30일 일봉 데이터 수집 (Chart API interval=1d)
  • Code 노드에서 RSI(14) 계산 함수 직접 작성 — 외부 라이브러리 금지
  • 5개 종목에 대해 RSI 계산 후 Google Sheets 저장
  • RSI ≤ 30 → "과매도", ≥ 70 → "과매수", 그 외 → "중립" 자동 라벨링
  • 매일 한국 장 마감 후 16:00 자동 실행

Starter Code (Code 노드)

// RSI 계산 함수 — 이 코드의 빈칸을 완성하세요
function calculateRSI(closes, period = 14) {
  if (closes.length < period + 1) return null;
  
  let gains = 0, losses = 0;
  
  // TODO: 첫 period 기간의 평균 상승/하락 계산
  for (let i = 1; i <= period; i++) {
    const diff = closes[i] - closes[i - 1];
    if (diff > 0) gains += diff;
    else losses += Math.abs(diff);
  }
  
  const avgGain = gains / period;
  const avgLoss = losses / period;
  
  if (avgLoss === 0) return 100;
  
  const rs = avgGain / avgLoss;
  return 100 - (100 / (1 + rs));
}

// 사용 예
const closes = $input.first().json.closes;  // 30일 종가 배열
const rsi = calculateRSI(closes, 14);

return [{ json: { rsi: rsi.toFixed(2), zone: rsi <= 30 ? 'oversold' : rsi >= 70 ? 'overbought' : 'neutral' } }];
Yahoo 응답에서 종가 배열 추출하기
Yahoo Chart API 응답 구조가 복잡합니다:
const result = $input.first().json.chart.result[0];
const closes = result.indicators.quote[0].close.filter(c => c !== null);

// 또는 안전하게:
const closes = ($json.chart?.result?.[0]?.indicators?.quote?.[0]?.close || [])
  .filter(c => c !== null);
null 값 필터링이 필수 (휴장일 데이터). 30일 중 실제 유효한 종가가 22~25개 정도.
채점 기준 (20점 만점)
A. RSI 계산 함수 정확성7점
B. 5종목 모두 적용4점
C. 과매수/과매도 자동 라벨링4점
D. Sheets 저장 형식 (RSI · Zone · Date)3점
E. 16:00 자동 실행 설정2점
📦 제출물
1. 워크플로 JSON
2. 5일 이상 누적된 RSI 기록 Sheets 링크
3. 과매도/과매수 구간 발생 시점 스크린샷 (하나라도)
✓ 제출 전 체크
🔴 REQUIRED — 과제 2
이동평균(MA) 3종 골든크로스 탐지기
배점 20

MA5, MA20, MA60을 동시 계산하고, 단기선이 장기선을 상향 돌파하는 골든 크로스 시그널을 자동 탐지합니다.

이동평균 정의
MA(N) = (최근 N일 종가의 합) / N
필수 요구사항
  • 과거 70일 이상 데이터 수집 (MA60 계산 위해)
  • MA5, MA20, MA60 동시 계산 함수 작성
  • 현재 MA5 > MA20 AND 전일 MA5 ≤ MA20 → "골든크로스" 탐지
  • 반대 조건 → "데드크로스" 탐지
  • 시그널 발생 시 Discord 알림 발송

MA 계산 함수 Starter

function calculateMA(closes, period) {
  if (closes.length < period) return null;
  const recent = closes.slice(-period);
  return recent.reduce((a, b) => a + b, 0) / period;
}

// 현재와 어제 두 시점의 MA를 계산해 크로스 탐지
const ma5_today = calculateMA(closes, 5);
const ma5_yesterday = calculateMA(closes.slice(0, -1), 5);
const ma20_today = calculateMA(closes, 20);
const ma20_yesterday = calculateMA(closes.slice(0, -1), 20);

const isGoldenCross = ma5_today > ma20_today && ma5_yesterday <= ma20_yesterday;
const isDeadCross  = ma5_today < ma20_today && ma5_yesterday >= ma20_yesterday;
⚠️ 자주 하는 실수: MA60 계산에 60일 데이터만 있으면 "당일 MA"는 가능하지만 "전일 MA"가 불가능. 최소 61일 이상 필요. 여유있게 70~80일 수집 권장.
채점 기준 (20점 만점)
A. MA 3종 정확 계산6점
B. 골든/데드크로스 탐지 로직6점
C. Discord 시그널 알림4점
D. IF 노드로 분기 처리2점
E. 시그널 로그 Sheets 저장2점
📦 제출물
1. 워크플로 JSON
2. 실제 발생한 골든/데드크로스 Discord 캡처 (과거 데이터 backfill 해서라도)
3. MA5/20/60 3개 라인을 그린 시각화 (Sheets 차트 or 외부 도구)
🔴 REQUIRED — 과제 3
볼린저 밴드 + 밴드 돌파 알림
배점 20

볼린저 밴드(20, 2σ)를 계산하고, 현재가가 상단/하단 밴드를 돌파하면 Discord에 알림 발송.

볼린저 밴드 공식
Middle = MA(20)
Upper = Middle + 2σ
Lower = Middle − 2σ
필수 요구사항
  • 표준편차(σ) 계산 함수 작성 — 외부 라이브러리 금지
  • Upper, Middle, Lower 밴드 3개 동시 계산
  • 현재가가 Upper 초과 → "상단 돌파 경고"
  • 현재가가 Lower 이하 → "하단 이탈 경고"
  • Band Width (밴드 폭) 계산: (Upper - Lower) / Middle × 100
표준편차 계산 함수
function calculateStdDev(values) {
  const mean = values.reduce((a,b) => a+b, 0) / values.length;
  const sqDiff = values.map(v => Math.pow(v - mean, 2));
  const variance = sqDiff.reduce((a,b) => a+b, 0) / values.length;
  return Math.sqrt(variance);
}

const recent20 = closes.slice(-20);
const middle = calculateMA(recent20, 20);
const std = calculateStdDev(recent20);
const upper = middle + 2 * std;
const lower = middle - 2 * std;
채점 기준 (20점 만점)
A. 표준편차 + 밴드 3종 정확성7점
B. 돌파/이탈 탐지5점
C. Band Width 계산 + 저장3점
D. Discord Embed 디자인3점
E. Switch 노드로 상/하단 분기2점
📦 제출물
1. 워크플로 JSON
2. 실제 밴드 돌파 Discord 캡처
3. Band Width의 시간 변화 (스퀴즈 구간 발견되면 별점)
🟣 ADVANCED — 과제 4
3지표 종합 시그널 엔진
배점 20

과제 1~3의 RSI + MA + 볼린저 3개 지표를 모두 합쳐, 각 지표의 시그널에 가중치를 부여한 종합 점수를 만듭니다.

필수 요구사항
  • 각 지표에서 -1 (강한 매도) ~ +1 (강한 매수) 점수 산출
  • 가중 평균: RSI × 0.4 + MA × 0.4 + Bollinger × 0.2
  • 종합 점수에 따라 5단계 분류: 강력매수 / 매수 / 중립 / 매도 / 강력매도
  • 결과를 Discord Embed에 색상 구분으로 발송 (강력매수=진녹, 매수=연녹, ...)
  • 매일 16:00 장 마감 후 실행

점수 산정 예시

// RSI 점수 (-1 ~ +1)
function rsiScore(rsi) {
  if (rsi <= 30) return +1;       // 과매도 → 매수
  if (rsi <= 40) return +0.5;
  if (rsi < 60)  return  0;       // 중립
  if (rsi < 70)  return -0.5;
  return -1;                           // 과매수 → 매도
}

// MA 점수 — 정배열/역배열 판단
function maScore(ma5, ma20, ma60) {
  if (ma5 > ma20 && ma20 > ma60) return +1;   // 완전 정배열
  if (ma5 > ma20) return +0.5;
  if (ma5 < ma20 && ma20 < ma60) return -1;   // 완전 역배열
  if (ma5 < ma20) return -0.5;
  return 0;
}

const total = rsiScore * 0.4 + maScore * 0.4 + bollScore * 0.2;
// -1.0 ~ +1.0 사이 값
채점 기준 (20점 만점)
A. 3지표 통합 로직 품질6점
B. 가중치 체계 타당성4점
C. 5단계 분류 정확성4점
D. Discord 색상 Embed 구현4점
E. 실제 발생 시그널 기록2점
🟣 ADVANCED — 과제 5
간이 백테스트 — 1년치 시그널 승률 측정
배점 20

과거 1년 데이터로 과제 4의 시그널을 백테스트해 승률을 측정합니다. "이 전략이 실제로 수익이 날까?"를 실증.

필수 요구사항
  • Yahoo Finance에서 1년치 일봉 수집 (interval=1d, range=1y)
  • 모든 거래일마다 시그널 계산 (~250개 데이터 포인트)
  • "강력매수" 시그널 발생 시 5일 후 종가 수익률 기록
  • 승률, 평균수익률, 최대손실, 샤프 비율 계산
  • 결과를 Google Sheets에 리포트 형식으로 정리

백테스트 결과 템플릿

Backtest Report — {ticker}

Period: 2025-04 ~ 2026-04
Signals fired: 23 (BUY) / 19 (SELL)

Win Rate (BUY):  61% (14/23)
Avg Return:      +2.3%
Max Drawdown:    -7.1%
Sharpe Ratio:    0.89

Conclusion: 전략이 유효하지만 승률이 낮아 개선 필요
⚠️ 주의: 백테스트 결과가 좋다고 미래에도 좋다는 보장 없음. Look-ahead bias에 주의 — "미래 데이터로 과거 시그널을 만들면 안됨". 계산할 때 각 시점에서 그 시점까지의 데이터만 사용.
채점 기준 (20점 만점)
A. 1년치 데이터 순회 로직5점
B. Look-ahead 없이 시그널 생성5점
C. 4개 메트릭 계산 정확성5점
D. 리포트 가독성·시각화3점
E. 시그널 개선 제안2점
Submit

📤 제출 방법 + 기한

⏰ 제출 기한: W3 수업 시작 전까지. 지연 시 하루당 -2점.
📝 W2 HOMEWORK COMPLETE
기술적 지표 · 매매 시그널 엔진
5 tasks · 100 pt · 4~8 hours
데이터 → 지표 → 시그널 → 알림, 의사결정 자동화의 기초가 완성됩니다