[#6] 파인스크립트 강좌 - 실전 함수와 사용방법

[#6] 파인스크립트 강좌 - 실전 함수와 사용방법
이번 편은 시리즈의 대미(大尾)를 장식하는 강의입니다.
앞서 변수·연산자·조건문·반복문을 모두 배웠으니, 이제 차트 위에서 실제 주문·시각화·디버깅까지 담당하는 핵심 함수들을 익혀 보겠습니다.
강의가 다소 길지만, 끝까지 따라오시면 “전략 하나를 처음부터 끝까지” 직접 구현하실 수 있습니다.

왜 ‘실전 함수’가 중요한가요?

파인스크립트는 기본적으로 데이터 계산에 특화된 언어이지만, 계산 결과를 행동으로 연결 하는 단계가 없으면 아무 일도 일어나지 않습니다.

  • 주문 함수로 포지션을 열고 닫고
  • 시각화 함수로 정보를 사용자가 볼 수 있게 표시하며
  • 로깅 함수로 오류나 중간 값을 확인해야

비로소 전략(Strategy) 또는 지표(Indicator) 로서 완성도가 올라갑니다.

매매(Order) 함수 ― strategy.* 패밀리

strategy.entry() : 포지션 진입의 핵심

strategy.entry(id, direction, qty, limit, stop, oca_name, oca_type, ...)
파라미터 필수 설명
id 주문 식별 문자열(예: "Long")
direction strategy.long 또는 strategy.short
qty 계약 수량(미지정 시 기본 설정 사용)
limit / stop 지정가·스탑가 진입
oca_* 서로 상쇄(OCA) 주문 그룹
 id고유해야 하며, 차트 우측 주문창에서 그대로 노출됩니다.

strategy.exit() : 스탑·타깃·트레일링까지 한 줄

strategy.exit(from_entry = "Long",
              stop  = price * 0.97,
              limit = price * 1.05,
              trail_points = 50)
  • from_entry 로 특정 진입 주문을 지정하고
  • stop·limit·trail_*손절·익절·추적 스탑을 동시에 설정합니다.

strategy.close() : 조건부 강제 청산

if ta.crossunder(close, sma20)
    strategy.close("Long")
  • strategy.close(id)시장가로 즉시 포지션을 닫습니다.
  • 배열 반복 안에서 호출하면 여러 포지션을 순회 청산하는 것도 가능합니다.

시각화 함수 ― label.* & Friends

label.new() : 차트에 ‘포스트잇’을 붙이듯

myLabel = label.new(x         = bar_index,
                    y         = high,
                    text      = "고점!",
                    color     = color.yellow,
                    textcolor = color.black,
                    style     = label.style_label_down,
                    size      = size.small)
  • x, y : 위치(바 인덱스·가격)
  • text : 표시할 문자열
  • color / textcolor / style / size : 시각적 속성

레이블 업데이트

if barstate.islastconfirmedhistory
    label.set_text(myLabel, "종가: " + str.tostring(close))
    label.set_tooltip(myLabel, "데이터 업데이트 완료")
  • label.set_*() 계열로 내용·색상·위치를 동적으로 바꿀 수 있어,
    실시간 수치 패널이나 알림용 레이블에 자주 쓰입니다.

디버깅 함수 ― log.info()로 콘솔 로그처럼!

Pine Script® 5부터는 Pine Logs 패널이 새롭게 추가되어 디버깅이 훨씬 쉬워졌습니다.
함수 색상 주 용도
log.info() 회색 일반 정보·중간 값 출력
log.warning() 주황 경고 메시지·예외 상황
log.error() 빨강 치명적 오류·즉시 확인 필요
if nz(rsiVal) > 80
    log.warning("RSI 과열 구간 진입: " + str.tostring(rsiVal))
  • 클릭하면 호출 지점으로 이동 → 버그 추적에 유용합니다.
  • 문자열 연결 시 str.tostring()로 타입 오류를 방지하세요.

필수 TA(Technical Analysis) 함수 한눈에 보기

ta.* 네임스페이스는 ’숫자 계산→패턴 판단‘을 돕는 고성능 빌트인 함수 모음입니다. 대부분 C++로 최적화돼 있어 직접 루프를 돌리는 것보다 빠르고 메모리 안전합니다.
분류 대표 함수 핵심 개념 & 예시
이동평균 ta.sma(src, len)
ta.ema(src, len)
단순·지수 이동평균.
sma20 = ta.sma(close, 20)
오실레이터 ta.rsi(src, len)
ta.stoch(close, high, low, lenK, lenD)
과매수·과매도 탐지.
rsiVal = ta.rsi(close, 14)
패턴 감지 ta.crossover(a, b)
ta.crossunder(a, b)
골든·데드 크로스.
longCond = ta.crossover(close, sma20)
통계/산술 ta.highest(src, len)
ta.lowest(src, len)
ta.atr(len)
최고·최저·ATR 등 변동성 측정.
변형 ta.change(src, len)
ta.percentile_nearest_rank(src, len, p)
상승폭·백분위 계산.
시그널 스무딩 ta.wma, ta.hma, ta.linreg 잡음 제거·추세선 적합.

빠른 예제 ― 다중 조건을 ta.* 하나로

bullish = ta.crossover(close, ta.sma(close, 20)) and ta.rsi(close, 14) < 60
if bullish
    label.new(bar_index, low, "매수 신호", color = color.lime)
  • ta.sma, ta.rsi, ta.crossover 세 가지를 조합해 1줄로 ‘추세 + 모멘텀’ 필터 완성.
  • 동일 로직을 직접 for 루프로 구현하면 성능이 수십 배 느려집니다.

기타 실무 함수 스피드런

카테고리 함수 한 줄 설명
표(Table) table.new() 차트 고정 패널로 여러 값을 깔끔하게 정리
알림(Alert) alert() 사용자 지정 텍스트로 TradingView 알림 발송
배열(Array) array.new_*() 멀티 심볼·멀티 타임프레임 데이터 캐싱
리스크 관리 strategy.risk.max_drawdown() 백테스트 중 최대 손실 제한

모두 익히면 복잡한 대시보드·멀티 자산 전략도 어렵지 않습니다.

30줄 통합 예제 ― “레이블 + 로깅 + 매매 + TA” 전략

//@version=5
strategy("Full-Stack Demo", overlay = true, default_qty_type = strategy.percent_of_equity, default_qty_value = 10)

// (1) 기본 지표
sma20   = ta.sma(close, 20)
rsiVal  = ta.rsi(close, 14)
atrVal  = ta.atr(14)

// (2) 진입 조건
longCond  = ta.crossover(close, sma20)  and rsiVal < 60
shortCond = ta.crossunder(close, sma20) and rsiVal > 40

// (3) 주문
if longCond
    strategy.entry("Long",  strategy.long)
    label.new(bar_index, low,  "Long ▶", color = color.lime, style = label.style_label_up)
    log.info("Long 진입 — RSI: " + str.tostring(rsiVal))

if shortCond
    strategy.entry("Short", strategy.short)
    label.new(bar_index, high, "Short ▼", color = color.red,  style = label.style_label_down)
    log.info("Short 진입 — RSI: " + str.tostring(rsiVal))

// (4) ATR 기반 포지션 관리
stopL  = close - atrVal * 1.5
limitL = close + atrVal * 3
stopS  = close + atrVal * 1.5
limitS = close - atrVal * 3

strategy.exit(from_entry="Long",  stop = stopL, limit = limitL)
strategy.exit(from_entry="Short", stop = stopS, limit = limitS)
  • ta.atr 로 동적 스탑·타깃.
  • 레이블로 시각 확인, 로그로 백테스트 추적, entry/exit로 체결.

실전에서 자주 만나는 오류 Best 5

증상 원인 해결책
“Unknown id” 메시지 strategy.exit()from_entry 오타 id 문자열 통일
레이블이 남발해 차트가 느려짐 label.new() 를 매 봉마다 생성 var label + label.set_*() 재활용
로그 스팸 반복문·다중 조건 안에서 log.info() 남용 호출 횟수 제한·조건 분기
주문 중복 동일 봉 내 여러 entry() 호출 strategy.opentrades == 0 체크
Qty = 0 오류 qty 계산에 0 또는 NA 포함 nz()로 기본값 지정

오늘의 핵심 정리

  1. strategy.entry/exit/close 로 _주문 풀스택_을 구현할 수 있습니다.
  2. label.newlabel.set_* 로 차트에 실시간 정보 패널을 만들 수 있습니다.
  3. log.info 는 콘솔 디버깅을 Pine Script에서도 누릴 수 있습니다.
  4. ta.* 함수를 우선 활용하면 빠르고 안전한 계산이 가능합니다.
  5. 실무에서는 성능 최적화(레이블 재사용, 로그 최소화) 가 완성도를 좌우합니다.

이제 여러분은 “계산 → 판단 → 행동 → 시각화 → 디버깅” 전 과정을 모두 다루실 수 있습니다.
차트 위에 자신만의 자동매매 전략을 올려 직접 수익 곡선을 확인해 보세요!