2009年7月30日 星期四

台指期轉檔程式 - perl 程式 2 (配合前支gettick3w.pl-自行下載交易檔)

配合前支程式 : 自期交所自行下載交易檔 perl 程式(win-XP) - gettick3w.pl

  1. 配合環境: windows xp sp2
  2. 程式名稱 : proc3w_tick.pl
  3. 程式目的 : 將當天交易檔分拆成台指期,小台,電指期,金指期當月分tick檔
  4. 程式碼



#!C:\Perl\bin\perl.exe

# 2009-06-25 change output file name
# 2009/6/25 Change directory to C:\\tick\\prg_perl3w\\
# 2009/6/18 For Win32 ActivePerl
# 2009-06-17 for move File to Storage Directory
# 2009-06-06 Process Tick and Make K-Line File

use POSIX qw(strftime);
use integer;

$workDir = 'C:\\tick\\prg_perl3w\\daily\\';
$tickDir = 'C:\\tick\\prg_perl3w\\tick\\';
# 可以改成 5 分K
# my $Minute5K = 5; # 5分K
my $Minute1K = 1; # 1分K

# 讀取最後交易日檔
my $LastTradingDays = "C:\\tick\\prg_perl3w\\last-trading-days";


$today = strftime "%Y%m%d", localtime;

$today_YY = substr $today, 0, 4;
$today_mm = substr $today, 4, 2;
$today_dd = substr $today, 6, 2;

$tick_day = $today_YY . "-" . $today_mm . "-" . $today_dd;

$wkMonth = &get_current_month_product($LastTradingDays);

print "Process $today Tick and Make $Minute1K Minute K-Line File..\n";

chdir $workDir;

&split_Tick ($today_YY, $today_mm, $today_dd, $wkMonth);

$tickdayfile = '???' . $today;

$daily_trade_file = 'Daily_' . $today_YY . '_' . $today_mm . '_' . $today_dd;

$saveDir = substr $today, 0, 6;
$tickStoreDir = $tickDir . $saveDir . '/';
$dailyStoreDir = $workDir . $saveDir . '/';

`C:\\tick\\prg_perl3w\\movefile2dir.pl $workDir $dailyStoreDir $daily_trade_file`;
`C:\\tick\\prg_perl3w\\movefile2dir.pl $workDir $tickStoreDir $tickdayfile`;

exit;

sub process_kline {
# in參數 $tickfile $KMinute

my $startHH = '08'; # 開始時
my $startMM = '45'; # 開始分
my $IdxK = -1; # idx
my $PreIdxK = -1; # idx

my $tickfile = $_[0];
my $KMinute = $_[1];

$workday = substr $tickfile, 3, 8;
my $kline_file = substr($tickfile, 0, 11) . '_' . $KMinute . 'k' . substr($tickfile, 11, 4);

open(infile, $tickfile) || die("Cannot open $tickfile.\n");
open(outfile, ">$kline_file");

print outfile "Date Time,Open,High,Low,Close,Vol\n";

# print "K File Processing...\n";

;

while(my $tk_record = )
{
chomp $tk_record;
$tk_record =~ s/ //g;
($tickTime, $tickPrice, $tickVol)=split(/,/ , $tk_record);

$tkTimeHh = substr $tickTime, 0, 2;
$tkTimeMm = substr $tickTime, 3, 2;
$tkTimeSs = substr $tickTime, 6, 2;

$IdxK = int(((($tkTimeHh - $startHH) * 60) + ($tkTimeMm - $startMM)) / $KMinute);
if ($IdxK == $PreIdxK) { # 同根k
if ($tickPrice > $HPrice) {
$HPrice = $tickPrice;
}
if ($tickPrice < $LPrice) {
$LPrice = $tickPrice;
}
$CPrice = $tickPrice;
$KVol = $KVol + $tickVol;
}
else {
if ($PreIdxK != -1){
print outfile $KTime,$OPrice,$HPrice,$LPrice,$CPrice,$KVol\n";
}
$OPrice = $tickPrice;
$HPrice = $tickPrice;
$LPrice = $tickPrice;
$CPrice = $tickPrice;
$KVol = $tickVol ;

my $KTimeHH = ((($IdxK + 1) * $KMinute) + ($startHH * 60) + $startMM) / 60 + 100;
my $KTimeMM = ((($IdxK + 1) * $KMinute) + ($startHH * 60) + $startMM) % 60 + 100;
$KTimeHH = substr $KTimeHH, 1, 2;
$KTimeMM = substr $KTimeMM, 1, 2;

$KTime = $tick_day . ' ' . $KTimeHH . ':' . $KTimeMM;
$PreIdxK = $IdxK;
}
}
if ($IdxK == $PreIdxK) {
# 同根k
print outfile "$KTime,$OPrice,$HPrice,$LPrice,$CPrice,$KVol\n";
}
close(outfile);
close(infile);
}

# get current month product. ex: 200906 (取得當月月分)
sub get_current_month_product{
my $LastTradingDays_file = $_[0];
open(open_LastTradingDays, $LastTradingDays_file)|| die("Cannot open $LastTradingDays_file.\n");
@recs = ;

for($row=@recs-1; $row >= 0; $row=$row-1)
{
my $LastTradingDays = $recs[$row];
if ($LastTradingDays >= $today ) {
$TradingDays = $LastTradingDays;
}
}
my $wkMonth = substr $TradingDays, 0, 6;

close(open_LastTradingDays);
return $wkMonth;
}

sub split_Tick {
chdir $workDir;
# in參數 $today_YY $today_mm $today_dd $wkMonth

$workday_YY = $_[0];
$workday_mm = $_[1];
$workday_dd = $_[2];
$workMonth = $_[3];

$workdayfile = $workday_YY . $workday_mm . $workday_dd;


$trade_file = 'Daily_' . $workday_YY . '_' . $workday_mm . '_' . $workday_dd . '.rpt';

my $TX_Product = 'TX'; # 台指
my $MTX_Product = 'MTX'; # 小台
my $TE_Product = 'TE'; # 電指期
my $TF_Product = 'TF'; # 金指期

# 2009-06-25 change output file name
$tx_tickfile = 'txf' . $workdayfile . '.csv'; # 台指
$mtx_tickfile = 'mxf' . $workdayfile . '.csv'; # 小台
$te_tickfile = 'exf' . $workdayfile . '.csv'; # 電指期
$tf_tickfile = 'fxf' . $workdayfile . '.csv'; # 金指期

open(read_file, $trade_file) || die("Cannot open $trade_file.\n");


open(out_tx, ">$tx_tickfile");
open(out_mtx,">$mtx_tickfile");
open(out_te, ">$te_tickfile");
open(out_tf, ">$tf_tickfile");

print out_tx "Date Time,Price,Vol\n";
print out_mtx "Date Time,Price,Vol\n";
print out_te "Date Time,Price,Vol\n";
print out_tf "Date Time,Price,Vol\n";

# print "Split Tick File Processing...\n";

while(my $record = )
{
chomp $record;
$record =~ s/ //g;
# 交易日期,商品代號,交割年月,成交時間,成交價格,成交數量(B+S),近月價格,遠月價格
($tDays, $tProduct, $tMonth, $tickTime, $tPrice, $tVol, $nPrice, $fPrice)=split(/,/ , $record);
# print "$tDays, $tProduct, $tMonth, $tickTime, $tPrice, $tVol, $nPrice, $fPrice\n";

$tVol = $tVol / 2;

$tTimeHh = substr $tickTime, 0, 2;
$tTimeMm = substr $tickTime, 2, 2;
$tTimeSs = substr $tickTime, 4, 2;

$tTime = $tTimeHh . ':' . $tTimeMm . ':' . $tTimeSs;

# 當月
if ($tMonth eq $workMonth)
{
if ($tProduct eq $TX_Product) { # 台指
print out_tx "$tTime,$tPrice,$tVol\n";
}
elsif ($tProduct eq $MTX_Product) { # 小台
print out_mtx "$tTime,$tPrice,$tVol\n";
}
elsif ($tProduct eq $TE_Product) { # 電指期
print out_te "$tTime,$tPrice,$tVol\n";
}
elsif ($tProduct eq $TF_Product) { # 金指期
print out_tf "$tTime,$tPrice,$tVol\n";
}
}
}

close(out_tf);
close(out_te);
close(out_mtx);
close(out_tx);

close(read_file);

&process_kline($tx_tickfile, $Minute1K);
}

參考我的 wiki : Process split tick - proc3w_tick.pl

5 則留言:

  1. 請問用這支轉檔程式可用來觸發下單程式嗎?

    回覆刪除
  2. 不行, 這只是將交易檔的不同商品tick分出來, 並轉成K線檔。

    回覆刪除
  3. 問個蠢問題(我完全是Perl的新手)
    這個程式可以用來轉期交所的歷史資料RPT檔嗎?
    可以把好幾天的RPT檔案結合到一個CSV裡面嗎?
    謝謝

    回覆刪除
  4. 這程式就是轉期交所的成交記錄, 以前的歷史資料可能要改一下, 台指期等的期貨代碼會不同, 還有這程式是抓當天日期,轉換成要處理的交易日期, 也要改.

    RPT檔案中包括當天所有的期貨成交記錄(還有不是當月的), 要用程式(或手動)分開, 成為當月單一產品的期貨成交記錄, 再用這當月單一產品期貨成交記錄來合併, 可以移除抬頭行後, 一直累加在新檔後面,就可以了.

    回覆刪除
  5. 網友 trilobite 來信提醒, 一分鐘k線有誤, 經比對後發現以前改了變數名稱, $tPrice 改成 $tickPrice, 忘了全部改完, 以至於最高低價是錯的(部份差約6~7點), 已改正。

    回覆刪除

聯絡表單

名稱

以電子郵件傳送 *

訊息 *