본문 바로가기
  • "Backtest, backtest, backtest." - Martin Schwartz
[백테스팅] 소개

[백테스팅 도구] 파인 스크립트 기본 문법

by Eirene 2022. 11. 25.
반응형

[백테스팅 도구] 파인 스크립트 기본 문법

트레이딩 뷰에서 제공하는 파인 스크립트

파인 스크립트 (Pine Script)는  트레이딩 뷰 내에서 고유의 전략이나 인디케이터를 만들어 차트에 쓸 수 있게 하는 트레이딩뷰에서 개발한 개발 언어입니다. 파인 스크립트 런타임은 트레이딩뷰의 차트에 있는 시간 별 (Time Series)에 대해 연산하여 차트에 정보를 출력하거나 별도의 인디케이터를 만들 수도 있고, 백테스팅을 위해 전략을 테스트할 수도 있습니다. 

본 글에서는 파인 스크립트 언어에 대해 기본적인 문법에 대해 제공 키워드 사용자 정의 함수와 더불어 자주 사용하는 코드로써, 변수 사용, 조건문, 분기문배열, 시간 관련에 대해 알아 보도록 하겠습니다.

자세한 트레이딩뷰와 파인 스크립트 관련 정보는 아래 WikiDocs에 있는 온라인북 참고 바랍니다.
[도서] : 트레이딩뷰 파인 스크립트 개발 : 기술적 지표, 신호, 전략, 백테스팅
 

트레이딩뷰 파인 스크립트 개발: 기술적 지표, 신호, 전략, 백테스팅

이 책는 트레이딩뷰(TradingView) 플랫폼에서 사용되는 프로그래밍 언어인 파인 스크립트(Pine Script)를 배우고 숙달하기 위한 궁극적인 가이드입니다. 이 포괄적인 …

wikidocs.net

 

파인 스크립트 제공 키워드, 빌트인 변수 및 함수

먼저 언어에서 제공하는 오퍼레이터(키워드)는 아래와 같습니다.

!=, %, %=, *, *=, +, +=, -, -=, /, /=, <, <=, ==, =>, >, >=, ?:, [], 
and, array, bool, box, color, export, false, float, for, for...in, if, 
import, int, label, line, linefill, matrix, not, or, series, simple, 
string, switch, table, true, var, varip, while

그리고 자체적으로 유용하게 사용 가능한 빌트인 변수도 제공합니다.

open		// 차트의 현재 시가
close		// 현재 바가 마감되었을 때의 종가 또는 아직 마감되지 않은 실시간 바의 마지막 거래 가격
high		// 현재 최고 가격
low		// 현재 최저 가격
volume		// 볼륨
hl2		// (high + low) / 2
hl3		// (high + low) / 3
hlcc4		// (high + low + close + close) / 4
ohlc4		// (open + high + loc + close) / 4
year		// 거래소 타임 존 기준 현재 바의 해
month		// 거래소 타임 존 기준 현재 바의 달
dayofmonth	// 거래소 타임 존 기준 현재 바의 날
hour		// 거래소 타임 존 기준 현재 바의 시간
minute		// 거래소 타임 존 기준 현재 바의 분
second		// 거래소 타임 존 기준 현재 바의 초
// ...

또한 빌트인 함수도 제공 합니다.

math.abs(), math.long(), math.max(), math.random(), ...			// 수학 관련
ta.sma(), ta.ema(), ta.mach(), ta.rsi(), ta,supertrend(), ...		// 기술적 분석 관련
request.dividends(), request.eanings(), request.financial(), ...	// 다른 심볼 정보
str.format(), str.length(), str.tonumber(), str.tostring(), ...		// 문자열 관련
input(), input.color(), input.int(), input.symbol(), ...		// 인풋 관련
color.grom_gradient(), color.new(), color.rgb(), ...			// 색깔 관련

 

사용자 정의 함수

빌트인 함수 외에 사용자가 함수를 정의 하기 위해서는 함수 라인 형태(1줄, 여러 줄)에 따라 2가지 형식으로 작성할 수 있습니다.

한 줄 함수 (Single-line Function)

함수에서 연산 한 값을 돌려줍니다.

// 함수 정의 예
f(x, y) => x + y

// 함수 사용 예
a = f(open, close)
b = f(2, 2)
c = f(open, 2)

여러 줄 함수 (Multi-line Function)

함수 내 마지막으로 연산된 값을 돌려줍니다.

// 함수 정의 예
geom_average(x, y) =>
    a = x*x
    b = y*y
    math.sqrt(a + b)

함수에서 여러 결과물(튜플 등)을 돌려 줄 수도 있습니다.

// 함수 정의
fun(x, y) =>
    a = x+y
    b = x-y
    [a, b]
    
// 함수 사용 예
[res0, res1] = fun(open, close)
plot(res0)
plot(res1)

 

변수 사용 예

변수는 아래와 같은 형태로 사용 가능합니다.

BULL_COLOR = color.lime
i = 1
len = input(20, "Length")
float f = 10.5
closeRoundedToTick = math.round_to_mintick(close)
st = ta.supertrend(4, 14)
var barRange = float(na)
var firstBarOpen = open
varip float lastClose = na
[macdLine, signalLine, histLine] = ta.macd(close, 12, 26, 9)
plotColor = if close > open
    color.green
else
    color.red

var와 := 를 사용하여 변수 재할당

최초 변수를 선언할 시에는 =를 사용하고, 추후에 변수 값을 변경할 때는 :=를 사용합니다.

// 변수 선언
var a = 5.0
var b = 1.0
var c = 0.0
if a > b
    // 변수 값 변경
    c := a
plot(c)

 

조건문 사용 예

if, else if, else

다른 언어들처럼 if, else if, else문을 사용할 수 있습니다.

if (ta.crossover(source, lower))
    strategy.entry("BBandLE", strategy.long, stop=lower,
                   oca_name="BollingerBands",
                   oca_type=strategy.oca.cancel, comment="BBandLE")
else if (ta.crossover(source, high))
    strategy.close()
else
    strategy.cancel(id="BBandLE")

위 코드에서 if문을 다른 문법처럼 쓸 수도 있지만, 아래 코드와 같이 값 할당 시에도 사용 가능합니다.

x = if close > open
    close

string barState = if barstate.islastconfirmedhistory
    "islastconfirmedhistory"
else if barstate.isnew
    "isnew"
else if barstate.isrealtime
    "isrealtime"
else
    "other"

switch

표현식과 같이 쓰는 경우는 아래와 같습니다.

string maType = input.string("EMA", "MA type", options = ["EMA", "SMA", "RMA", "WMA"])
int maLength = input.int(10, "MA length", minval = 2)

float ma = switch maType
    "EMA" => ta.ema(close, maLength)
    "SMA" => ta.sma(close, maLength)
    "RMA" => ta.rma(close, maLength)
    "WMA" => ta.wma(close, maLength)
    =>
        runtime.error("No matching MA type found.")
        float(na)

plot(ma)

표현식이 없는 경우는 아래와 같습니다.

bool longCondition  = ta.crossover( ta.sma(close, 14), ta.sma(close, 28))
bool shortCondition = ta.crossunder(ta.sma(close, 14), ta.sma(close, 28))

switch
    longCondition  => strategy.entry("Long ID", strategy.long)
    shortCondition => strategy.entry("Short ID", strategy.short)

 

분기문 사용 예

다른 언어처럼 for문과 while문 사용 가능합니다.

for

// for문 안에서 값 할당
MA_LENGTH = 10
sumOfCloses = 0.0
for offset = 0 to MA_LENGTH - 1
    sumOfCloses := sumOfCloses + close[offset]
inefficientMA = sumOfCloses / MA_LENGTH
plot(inefficientMA)

// for문 안에서 if문 사용
MA_LENGTH = 10
upBars = 0.0
for offset = 0 to MA_LENGTH - 1
    if close[offset] > open[offset]
        upBars := upBars + 1
plot(upBars)

while

int n = input.int(10, "Factorial of", minval=0)

factorial(int val = na) =>
    int counter = val
    int fact = 1
    result = while counter > 0
        fact := fact * counter
        counter := counter - 1
        fact

// Only evaluate the function on the first bar.
var answer = factorial(n)
plot(answer)

 

배열 사용 예

배열은 아래와 같은 형태로 선언할 수 있습니다.

float[] prices1 = na

prices2 = array.new_float(0)

prices3 = array.new_float(2, close)

statesArray = array.from(close > open, high != close)
bool[] statesArray = array.from(close > open, high != close)

// var 사용1
var a = array.new_float(0)
array.push(a, close)
if barstate.islast
    label.new(bar_index, 0, "Array size: " + str.tostring(array.size(a)) + "\nbar_index: " + str.tostring(bar_index), size = size.large)

// var 사용2
var int[] lengths = array.from(2, 12, 20, 50, 100, 200)

 

시간 사용 예

// Try this on chart AAPL,1
timeinrange(res, sess) => not na(time(res, sess, "America/New_York")) ? 1 : 0
plot(timeinrange("1", "1300-1400"), color=color.red)

// This plots 1.0 at every start of 10 minute bar on a 1 minute chart:
newbar(res) => ta.change(time(res)) == 0 ? 0 : 1
plot(newbar("10"))

t1 = time(timeframe.period, "0000-0000:23456")
bgcolor(t1 ? color.new(color.blue, 90) : na)

 

 

보다 자세한 파인 스크립트에 대한 자세한 정보는 트레이딩 뷰에서 제공하는 유저 매뉴얼, 레퍼런스 자료, 파인코더 리소스를 참고 부탁드립니다.

 

 

참고

728x90
반응형

댓글