Amibroker: Code dùng cho bộ lọc.

trungnghia

Moderator
Dù đối với đa số VCers Amibroker không không còn mới mẻ, việc sử dụng Amibroker, code trong Amibroker và cả việc lọc cổ phiếu không là vấn đề gì! Tuy nhiên, vẫn có một số bạn có ý tưởng nhưng không biết cách ứng dụng trong Amibroker để lọc cổ phiếu cho mình. Nhân có câu hỏi về vấn đề này, tôi trình bày một cách đơn giản để dùng Scan hoặc Explorer (trong AutoAnalysis của Amibroker) để lọc cổ phiếu.

I. Dùng Scan:

1. Thành phần tối thiểu:

Có thể lọc bằng Scan với cấu trúc code đơn giản nhất, gồm một hay nhiều dòng trong các dòng sau đây:
Buy = <điều kiện 1>;
Sell = <điều kiện 2>;
Short = <điều kiện 3>;
Cover = <điều kiện 4>;

Các thành phần trong cặp ngoặc nhọn <điều kiện> là biểu thức lôgích theo cú pháp code được Amibroker quy định.

2. Thí dụ:

a. Một thí dụ đơn giản nhất:

Buy = Close> MA(Close, 200);

hoặc:

Buy = Cross(EMA(C,13), MA(C,21)) AND V>50000;


Cũng với ý tưởng trên, đoạn code có thể được sử dụng phức tạp hơn (nhằm tạo được nhiều tùy chọn hơn khi sử dụng):

//Long MA
P = ParamField("Price field",-1);
Periods = Param("Periods", 100, 2, 400, 1 );
Buy = Close> MA( P, Periods );

b. Thí dụ dùng nhiều lệnh điều kiện với điều kiện phức tạp :

r1 = Param("Fast avg", 12, 2, 200, 1);
r2 = Param("Slow avg", 26, 2, 200, 1);
r3 = Param("Signal avg", 9, 2, 200, 1);
ml = MACD(r1, r2);
sl = Signal(r1, r2, r3);
Buy=Cross(ml, sl);
Sell = Cross(sl, ml);

hay:

LongMA = EMA(C, Param("Long Period", 50, 30, 100, 5));
ShortMA = EMA(C, Param("Short Period", 5, 3, 50, 1));
Buy = Cross(ShortMA, LongMA );
Sell = Cross(LongMA, ShortMA );


3. Kết quả:

Với:
Buy = Close> MA(Close, 200);

Có kết quả:

Ticker,Trade,Date,Close,
AGF,Buy,2015/04/10,20.7000
BBC,Buy,2015/04/10,57.0000
BIC,Buy,2015/04/10,16.9000
BID,Buy,2015/04/10,19.0000
BMI,Buy,2015/04/10,17.3000
BMP,Buy,2015/04/10,81.0000
...

Với:

Buy = Cross(EMA(C,13), MA(C,21)) AND V>50000;

Kết quả nhận được:

Ticker,Trade,Date,Close,
BSI,Buy,2015/04/10,11.0000
JVC,Buy,2015/04/10,21.7000
VHC,Buy,2015/04/10,40.2000
VIS,Buy,2015/04/10,7.7000

Còn với:

LongMA = EMA(C, Param("Long Period", 50, 30, 100, 5));
ShortMA = EMA(C, Param("Short Period", 5, 3, 50, 1));
Buy = Cross(ShortMA, LongMA );
Sell = Cross(LongMA, ShortMA );

Kết quả sẽ có:

Ticker,Trade,Date,Close,
ABT,Sell,2015/04/10,51.0000
BCI,Sell,2015/04/10,20.8000
CYC,Buy,2015/04/10,3.9000
DQC,Buy,2015/04/10,57.5000
GTA,Buy,2015/04/10,16.0000
...

4. Thành phần kết quả được xuất ra có điểm chung: Gồm các cột mặc định: Ticker, Trade, Date và Close


II. Dùng Explorer:

Để dùng Explorer, trong code không dùng các dòng lệnh với Buy, Sell, Short hay Cover mà dùng Filter:

Filter = <điều kiện>;

<điều kiện> cũng là biểu thức lôgích.

Explorer đi kèm với tối thiểu 1 lệnh khai báo cột thông tin xuất ra và cho phép xuất ra các cột dữ liệu như ý muốn. Để xuất ra các cột thông tin, thường có thể dùng thêm các câu lệnh: AddColumn (được dùng xuất dữ liệu số) hoặc AddTextColumn (được dùng xuất dữ liệu chuỗi - text).

AddColumn(<Tên Dữ liệu>,<Tên cột>,<format>);
<Tên Dữ liệu> - Biến hoặc các biểu thức chứa dữ liệu dạng số muốn xuất ra.
<Tên cột> - Tiêu đề của cột sẽ được hiển thị.
<format> - dạng dữ liệu được xuất ra

AddTextColumn(<Tên Dữ liệu>,<Tên cột>);

Thí dụ:

Filter = Cross(EMA(C, 13), MA(C,21)) AND V>50000;
AddColumn(EMA(C, 13),"EMA-13",1.2);
AddColumn(MA(C, 21),"MA-21",1.2);
AddColumn(Ref(C, -4),"Close-4",1.2);
AddColumn(C,"Close",1.2);

Kết quả xuất ra:

Ticker,Date/Time,EMA-13,MA-21,Close-4,Close,
BIC,2015/04/09,16.06,16.02,15.80,17.20
BID,2015/04/08,17.91,17.88,17.90,18.50
BSI,2015/04/10,10.81,10.81,10.50,11.00
CCL,2015/04/09,4.04,4.03,4.00,4.10
CII,2015/04/07,18.57,18.53,18.20,19.30
GTN,2015/04/09,15.99,15.97,15.80,16.40
...

Hai cột đầu Ticker và Date/Time là mặc định (luôn luôn xuất hiện). Trong đó, Date/Time có format phụ thuộc vào khai báo trong Region and Language (Control Panel).

Các cột còn lại EMA-13, MA-21, Close-4 và Close là do 4 lệnh AddColumn đã khai báo ở trên.

Một trong những ứng dụng mà tôi đã dùng để xuất file EOD Upto ....txt là đoạn code sau:

Filter = 1;
AddColumn(O,"Open");
AddColumn(H,"High");
AddColumn(L,"Low");
AddColumn(C,"Close");
AddColumn(V,"Volume", 1.0);

.
 
Anh Trung Nghĩa ơi,
em làm file lọc tất cả cp nào có ngày lọc cuối cùng có đường trix (5) cắt trix (9), nhưng lọc không ra anh ơi, nhờ anh chỉ giúp

_SECTION_BEGIN("TRIX 5-9");
r1 = Param("Periods", 5, 2, 200, 1 );
Plot( Trix( 5 ), _DEFAULT_NAME(), ParamColor("color", colorCycle ), ParamStyle("Style");
r2 = Param("Periods", 9, 2, 200, 1 );
Plot( Trix( 9 ), _DEFAULT_NAME(), ParamColor("color", colorCycle ), ParamStyle("Style");
Buy = Cross(r1, r2) AND V > 20000;
_SECTION_END();
 
Anh Trung Nghĩa ơi, xem giúp file code sau giúp e với ạ. Trước e vẫn sử dụng được code này trên amibroker nhưng gần đây lại không dùng được nữa. A hỗ trợ giúp e với ạ

_SECTION_BEGIN("Portfolio filter");
eqname = "~~~EQUITY";
if( Name() != eqname ) SetForeign( eqname );
eq = Close;
Cash = Low;

dr = eq - Highest(eq);
bslh = HighestBars(eq);
GraphZOrder=1;
Plot(eq, "Portfolio Equity", colorLightBlue, styleArea );
if( ParamToggle("Show Cash", "No|Yes", 1 ) ) Plot(cash, "Cash", colorGreen, styleArea );
if( ParamToggle("Show Drawdown", "No|Yes", 1 ) ) Plot(dr, "Drawdown", colorDarkRed, styleArea );
if( ParamToggle("Show #bars since last high", "No|Yes", 0 ) ) Plot(bslh, "#bars since last high", colorDarkYellow, styleLine | styleOwnScale, 0, 10 * LastValue( Highest( bslh ) ) );
islastbar = Status("lastbarintest");
isfirstbar = Status("firstbarintest");
bar = BarIndex();
firstbar = LastValue( ValueWhen( isfirstbar, bar ) );
lastbar = LastValue( ValueWhen( islastbar, bar ) );
al = LastValue( ValueWhen( islastbar, LinRegSlope( eq, Lastbar - firstbar + 1 ) ) );
bl = LastValue( ValueWhen( islastbar, LinRegIntercept( eq, Lastbar - firstbar + 1 ) ) );
Lr = al * ( BarIndex() - firstbar ) + bl;
Lr = IIf( bar >= firstbar AND bar <= lastbar , Lr, Null );
if( ParamToggle("Show lin. reg.", "No|Yes", 0 ) )Plot( Lr , "Linear Reg", colorRed, styleThick );

function PercentR( periods )
{
return -100 * ( HHV( H, periods ) - C )/( HHV( H, periods ) - LLV( L, periods ) );
}

Plot( PercentR( Param("Periods", 14, 2, 100 ) ),
_DEFAULT_NAME(),
ParamColor("Color", ColorCycle ) );

PL = Param("PL",14,4,45,1);
ALen = PL;
uptrend=PDI()>MDI()AND Signal()<MACD();
downtrend=MDI()>PDI()AND Signal()>MACD();
AroonUp = 100 * (ALen - (HHVBars(H, ALen + 1))) / Alen;
AroonDn = 100 * (ALen - (LLVBars(L, ALen + 1))) / ALen;
DK3=Cross(AroonUp,AroonDn);
DK4=Cross(AroonDn,AroonUp);
if(uptrend=True)
{DK1=AroonUp>70;
DK2=AroonDn<30;
}
else
if(downtrend=True)
{DK1=AroonUp<30;
DK2=AroonDn>70;
}
f1=AroonUp-AroonDn;

SetChartOptions(0,chartShowArrows|chartShowDates);
_N(Title = StrFormat("{{NAME}} - {{INTERVAL}} {{DATE}} Open %g, Hi %g, Lo %g, Close %g (%.1f%%) Vol " +WriteVal( V, 1.0 ) +" {{VALUES}}", O, H, L, C, SelectedValue( ROC( C, 1 )) ));
Plot( C, "Close", ParamColor("Color", colorBlack ), styleNoTitle | ParamStyle("Style") | GetPriceStyle() );
if( ParamToggle("Tooltip shows", "All Values|Only Prices" ) )
{
ToolTip=StrFormat("Open: %g\nHigh: %g\nLow: %g\nClose: %g (%.1f%%)\nVolume: "+NumToStr( V, 1 ), O, H, L, C, SelectedValue( ROC( C, 1 )));
}

SL = ( HHV( H, 26 ) + LLV( L, 26) )/2;
TL = ( HHV( H, 9 ) + LLV( L, 9 ) )/2;
//DL = Ref( C, 26 );
DL=C;
Span1 = (( SL + TL )/2);
Span2 = (HHV( H, 52) + LLV(L, 52))/2;

Plot(SL,"Kijun sen",colorBlue);
Plot(TL,"Tenkan Sen",colorRed);
Plot(DL,"Chikou Span",colorBrightGreen,styleLine,Null,Null,-26);
Plot(Span1,"Span A",colorLightOrange,1,0,0,26);
Plot(Span2,"Span B",colorGrey40,1,0,0,26);
PlotOHLC(Span1,Span2,Span1,Span2,"",IIf(Span1>Span2,colorBrightGreen,colorLightGrey),styleCloud|4096,0,0,26);

_SECTION_BEGIN("Chaikin Money Flow");

function CMF(r1)
{
Graph0=Sum(IIf( H>L && V>0,((( C-L )-( H-C )) / ( H-L ))*V,0),r1) / Sum(V,r1);

dynamic_color = IIf( Graph0> 0, colorGreen, colorRed );

Plot(Graph0, "Chaikin Money Flow ("+r1+")", dynamic_color, styleHistogram | styleThick);

}

r1=Param("Periods", 21);
CMF(r1);


k1 = Param( "k1", 14, 2, 200, 1 );
Plot( CCI(k1), _DEFAULT_NAME(), ParamColor( "Color", colorCycle ), ParamStyle("Style") );


e1 = Param("e1", 9, 2, 200, 1 );
Plot( Trix(e1), _DEFAULT_NAME(), ParamColor("color", colorCycle ), ParamStyle("Style") );





Filter=(eq OR Low OR dr) AND V*C>=1000000;

Portfolio=ExRem(eq,eq); Cash=ExRem(Low,Low); Drawdown=ExRem(dr,dr);
AddColumn(Volume,"Volume"); AddColumn(MA(Volume,15),"MA(Volume,15)"); AddColumn(Open,"Price Open"); AddColumn(High,"Price high"); AddColumn(eq,"Portfolio(Price close)"); AddColumn(Low,"Cash(Price Low)"); AddColumn(dr,"Drawdown"); AddColumn(MA(Close,15),"MA(15)"); AddColumn(MA(Close,45),"MA(45)"); AddColumn(MA(Close,100),"MA(100)"); AddColumn(MA(Close,200),"MA(200)"); AddColumn(BBandTop(Close,15,2),"BBTop"); AddColumn(BBandBot(Close,15,2),"BBbot"); AddColumn(SL,"Kijun sen"); AddColumn(TL,"Tenkan Sen"); AddColumn(DL,"Chikou Span"); AddColumn(Span1,"Senkou Span A"); AddColumn(Span2,"Senkou Span B"); AddColumn(MACD(12,26),"MACD(12,26)"); AddColumn(Signal(12,26,9),"Signal(12,26,9)"); AddColumn(MACD(12,26)-Signal(12,26,9),"MACD Histogram"); AddColumn(RSI(15),"RSI(15)"); AddColumn(StochK(15,3),"%K(15,3)"); AddColumn(StochD(15,3,3),"%D(15,3,3)"); AddColumn(MFI(14),"MFI(14)"); AddColumn(MA(MFI(14),15),"MA(MFI(14),15)"); AddColumn(PercentR(14),"William's %R(14)"); AddColumn(Graph0,"Chaikin money Flow"); AddColumn(ADX(14),"ADX"); AddColumn(PDI(14)," +DI"); AddColumn(MDI(14)," -DI"); AddColumn(AroonUp,"AroonUP"); AddColumn(AroonDn,"AroonDown"); AddColumn(f1,"Aroon Oscillator"); AddColumn(CCI(k1),"CCI"); AddColumn(Trix(e1),"Trix"); AddColumn(Ultimate(7),"Ultimate");
_SECTION_END();
 
Back
Top