Example #1
0
    def kline_merge_strategy(k_min = 30,start_date = '20200102',symbols=['IC2001.CFE']):
        '''
        用tick合成一天之内分钟级别的k线
        example:
        ---------
        k_min = 30 : tick合成30minK
        kcut_res_data = K_cut.kline_merge_strategy(k_min = 30,start_date = '20200102',symbols=['IC2001.CFE'])
        '''

        tick_data_batch = D.query_tsdata(datasource='future_tick', symbols=symbols,\
                                         fields='price',start=start_date, end=start_date, delivery_mode='batch_by_symbol')
        for d in tick_data_batch:
            tick_data = d

        tick_data = tick_data[start_date + ' 09:30:00':start_date + ' 15:00:00']
        kcut_res_data = K_cut.aggre_tick(tick_data = tick_data,m = 60*k_min,n = 60*k_min)
        #调整输出格式
        kcut_res_data=kcut_res_data.reset_index()
        kcut_res_data=kcut_res_data.rename(columns={'Symbol':'code','index':'DATETIME'})
        kcut_res_data['DATETIME'] = kcut_res_data['DATETIME'].apply(lambda x:pd.Timestamp(x.strftime('%Y-%m-%d %H:%M:%S')))
        kcut_res_data['code'] = symbols[0][:-1]
        kcut_res_data.drop('label',axis = 1,inplace = True)
        kcut_res_data.sort_values('DATETIME',inplace = True)
        #检查是否有重复行
        if any(kcut_res_data['DATETIME'].duplicated()):
            print('warning: kline_merge_strategy输出有重复时间戳')
            return
        else:
            pass
        return kcut_res_data
Example #2
0
    def long_Kline_merge(start = '20190102',end = '20191231',k_min = 1):
        '''
        获取从start到end这段时间内,合成k_min分钟K线。
        '''
        # 获取交易日
        trading_day_data = D.query_ext_factor(datasource='wind_eod_index_price', symbols=['000001.SH'],\
                                              fields=['S_DQ_CLOSE'], start=start, end=end)
        trading_day_data.reset_index(inplace = True)
        trading_day_data.rename({'ts':'trading_day'},axis = 1,inplace= True)
        trading_day_data =trading_day_data['trading_day']
        trading_day_data = trading_day_data.apply(lambda x :x.strftime('%Y%m%d') )
        #获取 IC
        IC_data = backtest.get_IC_date(start = start,end = end)
        #使用class,并concat
        kline_df = pd.DataFrame()
        for start_date in trading_day_data:
            symbols = []
            symbols.append(IC_data[(IC_data['ENDDATE'] >= start_date) &
                               (IC_data['STARTDATE'] <= start_date)]['FS_MAPPING_WINDCODE'].iloc[0])
            try:
                kline= K_cut.kline_merge_strategy(k_min = k_min,start_date = start_date,symbols=symbols)
            except TypeError:
                pass
            else:
                kline_df = pd.concat([kline_df,kline]).reset_index(drop = True)

        return kline_df
Example #3
0
    def get_lab_kline(start = '20190102',end = '20191231',k_min_high_level = 1,code = 'IC00.CFE'):
        '''
        获取lab平台上的股指期货K_line数据
        example:
        ---------
        prices = DataProcess.get_lab_kline(start = '20190102',end = '20191231',k_min_high_level = 1,code = 'IC00.CFE')

        '''

        data = D.query_tsdata(datasource=f'future_kline_{k_min_high_level}min', symbols=ContFutureSymbolFilter(code), fields='*', start=start, end=end)
        prices_list = []
        for df in data:
    #             #xhq modify
    #             df.index = pd.Series(df.index).shift(-1)
    #             df = df.iloc[:-1,:]
    #             ###
            prices_list.append(df)
        prices_df = pd.concat(prices_list)

        prices = prices_df[['Symbol', 'open', 'high', 'low', 'close']]
        prices.reset_index(inplace=True)
        prices = prices.rename(columns={'index':'DATETIME', 'Symbol': 'code'}) 

        return prices
Example #4
0
# -*- coding: utf-8 -*-
# @Time     : 2020/7/3 20:33
# @Author   :Xie Huiqin
# @File     : pre_part.py
# @Software : orient_lab/jupyter notebook



import pandas as pd
import numpy as np
import datetime
from market_timing_lab import MeanReversion
from algoqi.data import D
D.load()

from backtest_class import backtest

class interval:
    """
    Some idea from 缠中说禅.

    Examples
    ---------
    import numpy as np
    import pandas as pd
    from market_timing_lab import MeanReversion
    from algoqi.data import D
    from pre_part import *
    D.load()
    #IC2006.CF,1minK分钟数据
    data=D.query_tsdata(datasource='future_kline_1min', symbols=['IC2006.CF'], fields=['open','high','low','close'], 
Example #5
0
from algoqi.data import D, plotutils
D.switch_zxzx_client(access_key='e7e2de63f95674632824ed6b2be8dd1f', secret_key='d43ca617fe7048e4ccfb158dde8e1c32')
D.load()
import pandas as pd
import numpy as np

class ContFutureSymbolFilter(D.FutContContractFilter):
    '''
    当月合约筛选器
    examle:
    ---------
    symbols=ContFutureSymbolFilter(code)
    '''
    @staticmethod
    def future_suffix_replace(symbol_str: str):
        return symbol_str if '.CFE' not in symbol_str[0] else [symbol_str[0].replace(".CFE", ".CF")]

    def symbols_during(self, start_dt: str, end_dt: str):
        main_contracts_df = self._query_main_contract(symbols=self.symbols, start=start_dt, end=end_dt)
        if not main_contracts_df.empty:
            cont_list = []
            for i in range(len(main_contracts_df)):
                sub_cont = (main_contracts_df.iloc[i].symbol, main_contracts_df.iloc[i].start,
                            main_contracts_df.iloc[i].end, self.future_suffix_replace([main_contracts_df.iloc[i].mapping_symbol]))
                cont_list.append(sub_cont)
        return cont_list
               
class DataProcess:
    
    @staticmethod
    def get_lab_kline(start = '20190102',end = '20191231',k_min_high_level = 1,code = 'IC00.CFE'):
Example #6
0
    def bt_long(py_path='./final_5min.py',
                code='IC00.CFE',
                start='20190102',
                end='20191231',
                N=5,
                per_size=1,
                save=False,
                save_path='./final_5min.pkl',
                save_name='final_5min',
                k_min_high_level=1,
                k_min_low_level=1,
                use_tick_merge=False):
        '''
        return:
        -----------
        trades_df: 交易记录
        logs_df: 日志记录
        
        target
        -----------
        做长期回测,如一年
        
        parameter
        -----------
        py_path:策略文件路径
        code:获取当月合约,统一使用'IC00.CFE'
        start:回测开始时间(必须是交易日)
        end: 回测结束时间
        N: 时间切割策略中,回测使用的K线数据做几次切割。如:N = 5(使用5minK线)代表将5minK线切割5次,生成5套5minK线数据。
        per_size: 单次交易购买的合约数,一般情况下,使用per_size = 1
        save: 是否存储回测过程中交易和日志的中间结果:trades_df,logs_df
        save_path: 交易和日志的中间结果的存储路径
        save_name: 建议使用策略文件名,或者在策略文件名上加一些尾注
        k_min_high_level : (int)在第三买卖点策略中标识计算中枢的K线级别,如k_min_high_level =30 表示计算中枢的高级K线是30min K线
        k_min_low_level :  (int)在第三买卖点策略中标识计算笔的K线级别
        use_tick_merge : use_tick_merge = True,使用tick数据合成K线;use_tick_merge = False,使用平台提供的K线数据。        
        
        '''

        symbol = code  # 回测品种
        beg_date = start  # 回测开始时间,开始时间不能是周末
        end_date = end  # 回测结束时间

        symbols_list = D.CONT_FUT('IC00.CFE').symbols_during(
            beg_date, end_date)
        start = [symbols_list[i][1] for i in range(0, len(symbols_list))]
        end = [symbols_list[i][2] for i in range(0, len(symbols_list))]
        code = [
            symbols_list[i][3][0] + 'E' for i in range(0, len(symbols_list))
        ]

        res_trades = []  # 构造空的dataframe
        res_log = []
        for i in range(0, len(symbols_list)):

            if i > 0: j = i - 1
            else: j = 0

            params_dict = {
                'symbol': code[i],
                'per_size': per_size,
                'start': start[i],
                'latest_end': end[j],
                'first_start': start[0],
                'last_end': end[-1],
                'end': end[i],
                'N': N,
                'long_short': 'long',
                'py_name': save_name,
                'k_min_high_level': k_min_high_level,
                'k_min_low_level': k_min_low_level,
                'use_tick_merge': use_tick_merge
            }

            def params_func(*args, **kwargs):
                return {
                    'symbol': code[i],
                    'per_size': per_size,
                    'start': start[i],
                    'latest_end': end[j],
                    'first_start': start[0],
                    'last_end': end[-1],
                    'end': end[i],
                    'N': N,
                    'long_short': 'long',
                    'py_name': save_name,
                    'k_min_high_level': k_min_high_level,
                    'k_min_low_level': k_min_low_level,
                    'use_tick_merge': use_tick_merge
                }

            print('\n', start[i], '-', end[i])
            config = BacktestConfig(sub_config=[])
            config.start_ts = start[i]
            config.end_ts = end[i]
            # config.fields = ["B1", "S1"]
            config.fields = "*"
            config.split = None
            config.datasource = "future_tick"

            # config.init_positions = [("AU1912", LongShortType.LONG, 0), \\("AU1912", LongShortType.SHORT, 0)]
            config.init_positions = []
            config.symbols = [code[i]]  #这里是列表,一定要注意数据结构
            config.param = params_dict

            res = AQ.backtest_local(py_path,
                                    config,
                                    params_dict=params_func,
                                    convert_to_df=True)
            res_log.append(res.logs)
            res_trades.append(res.trades)
            #中间存储
            if save:
                trades_df0 = pd.concat(res_trades)
                logs_df0 = pd.concat(res_log)
                try:
                    loc = save_path.rindex('/')

                    save_path_trades = list(save_path)
                    save_path_trades.insert(loc + 1, 'trades_')
                    save_path_trades = ''.join(save_path_trades)

                    save_path_logs = list(save_path)
                    save_path_logs.insert(loc + 1, 'logs_')
                    save_path_logs = ''.join(save_path_logs)

                except Exception as e:
                    raise ValueError(r'Save_path must contain at least one /')

                trades_df0.to_pickle(save_path_trades)
                logs_df0.to_pickle(save_path_logs)

        trades_df = pd.concat(res_trades)  #输出的是list,要转化为dataframe
        logs_df = pd.concat(res_log)  #输出的是list,要转化为dataframe
        return trades_df, logs_df
Example #7
0
def on_init(init_param, ctx: Context, U: UserSpace):
    ctx.log("initialize params")  # 日志

    long_or_short: str = init_param['long_short']
    if long_or_short == 'long':
        symbol = init_param['symbol']
        symbols = symbol[:-1]  # .CF
    else:
        # tick数据是.CFE;1min_kline是.CF
        symbol: str = init_param['symbol']  # 初始化参数
        # 'IC00.CFE'
        symbols = symbol
        symbol = symbol + 'E'
    U.py_name :str = init_param['py_name']
    U.first_start: str = init_param['first_start']
    U.last_end: str = init_param['last_end']
    U.start: str = init_param['start']
        
    #latest_end:本次合约之前一个合约的结束日期
    U.latest_end : str = init_param['latest_end']
        
    U.end: str = init_param['end']
    U.per_size: int = init_param['per_size']
    U.k_min_high_level: int = init_param['k_min_high_level'] 
    U.k_min_low_level: int = init_param['k_min_low_level']
    U.use_tick_merge = init_param['use_tick_merge']
    #     N :int =  init_param['N']

    ctx.subscribe_tick([symbol], fields=[TickFields.TRADE_PRICE,
                                         TickFields.B1, TickFields.S1,
                                         TickFields.SV1, TickFields.BV1])

    ctx.subscribe_time("09:45:00", "market_start")  # 开盘前16min不开仓
    ctx.subscribe_time("11:30:00", "market_suspend")
    ctx.subscribe_time("13:00:00", "market_start")
    ctx.subscribe_time("15:00:00", "market_almost_close")  # 收盘前15min完全平仓 修改:收盘前30min只平仓不开仓

    today = ctx.today().strftime('%Y%m%d')


    if today == U.start:

#         #使用tick合成的一段时间K线(pkl文件), 导入pkl,加快运行速度【数据1】
#         U.raw_prices = pd.read_pickle(f'./第三买卖点/{U.k_min_low_level}minK_20190102_20191231.pkl')
#         U.raw_prices_high_level = pd.read_pickle(f'./第三买卖点/{U.k_min_high_level}minK_20190102_20191231.pkl')

        #使用平台数据【数据2】或者使用【数据3】
        pass
        
        
#   【数据1】
#     now_date = ctx.today().strftime('%Y-%m-%d')
#     next_date = (ctx.today() + timedelta(days=1)).strftime('%Y-%m-%d')

#     prices = U.raw_prices[(U.raw_prices['DATETIME'] <= next_date) & (U.raw_prices['DATETIME'] >= now_date)]

#     prices_high_level = U.raw_prices_high_level[(U.raw_prices_high_level['DATETIME'] <= next_date)
#                                                 & (U.raw_prices_high_level['DATETIME'] >= now_date)]


    if U.use_tick_merge:
    #     使用tick合成的K线,每日计算【数据3】
        prices = K_cut.kline_merge_strategy(k_min = U.k_min_low_level,start_date = today,symbols=[symbol])
        prices_high_level = K_cut.kline_merge_strategy(k_min = U.k_min_high_level,start_date = today,symbols=[symbol])

        
    else:
    #   【数据2】
        curDate = ctx.today().strftime('%Y%m%d')

        data = D.query_tsdata(datasource=f'future_kline_{U.k_min_low_level}min', symbols=[symbols], fields = ['open','high','low','close'],\
        start = curDate, end=curDate, delivery_mode=D.DataDeliveryMode.DIRECT)

        data_high_level = D.query_tsdata(datasource=f'future_kline_{U.k_min_high_level}min', symbols=[symbols], fields = ['open','high','low','close'],\
        start = curDate, end=curDate, delivery_mode=D.DataDeliveryMode.DIRECT)
        try:
            # 检查是否发生数据缺失,缺失则跳过
            data = data.reset_index()
            data_high_level = data_high_level.reset_index()

        except AttributeError:
            print('\n',curDate,':数据缺失,跳过该日。')
            return
        
        prices = data.rename(columns={'Symbol': 'code', 'index': 'DATETIME'})
        prices_high_level = data_high_level.rename(columns={'Symbol': 'code', 'index': 'DATETIME'})
#         print(prices_high_level.iloc[:10,:])
        
    if len(prices) == 0 or len(prices_high_level) == 0:
        return



    ###input###
    # 计算每天前15min的数据

    if today == U.start:
        if today == U.first_start:
            #创建存储文件夹
            try:
                import os 
                os.mkdir(f'./第三买卖点/strategy_save/{U.py_name}_{U.first_start}_{U.last_end}')
            except FileExistsError:
                pass
                
            U.high_level_begin_time = prices_high_level['DATETIME'].iloc[0].strftime('%Y-%m-%d %H:%M:%S')

            # 回测第一天,计算初始值
            U.last_trading_point_time = 'init_trading_point_time'
            U.last_open = 'init_open'
            # 初始化中枢和三买df
            U.pivot_df = pd.DataFrame()
            U.three_point_df = pd.DataFrame()

            prices_init = prices[prices['DATETIME'] <= U.high_level_begin_time]
            prices_init_high_level = prices_high_level[prices_high_level['DATETIME'] <= U.high_level_begin_time]

            prices_adj, prices_part, prices_adj_high_level, prices_part_high_level, pivot_latest, trading_point_level_3 \
                = three_point.three_point_init_level2(prices_init, prices_init_high_level)

            U.pivot_df = U.pivot_df.append(pd.DataFrame({U.high_level_begin_time: pivot_latest}).T)
            
            if trading_point_level_3 != {}:
                U.three_point_df = U.three_point_df.append(
                    pd.DataFrame({U.high_level_begin_time: trading_point_level_3}).T)
            
            if pd.Timestamp(U.first_start + ' 09:45:00').strftime('%Y-%m-%d %H:%M:%S') > U.high_level_begin_time:
                prices_init = prices[(U.high_level_begin_time < prices['DATETIME'] )&(prices['DATETIME'] <= today+ ' 09:45:00')]
#                 print('\n*****',prices_init)
                for datetime in prices_init['DATETIME']:
                    prices_latest = prices.loc[prices['DATETIME'] == datetime, :]
                    prices_latest_high_level = prices_high_level.loc[prices_high_level['DATETIME'] == datetime, :]
                    prices_adj, prices_part, prices_adj_high_level, prices_part_high_level, pivot_latest, trading_point_level_3 = \
                        three_point.three_point_latest_level2_v0827(prices_latest, prices_latest_high_level, prices_adj,
                                                              prices_part, \
                                                              prices_adj_high_level, prices_part_high_level, pivot_latest,
                                                              trading_point_level_3)

                    U.pivot_df = U.pivot_df.append(pd.DataFrame({datetime.strftime('%Y-%m-%d %H:%M:%S'): pivot_latest}).T)
                    if trading_point_level_3 != {}:
                        U.three_point_df = U.three_point_df.append(
                            pd.DataFrame({datetime.strftime('%Y-%m-%d %H:%M:%S'): trading_point_level_3}).T)
            else:
                pass
            U.compare_time = max(pd.Timestamp(U.first_start + ' 09:45:00').strftime('%Y-%m-%d %H:%M:%S'),U.high_level_begin_time)



        else:
            # 承接上一产品信息
            prices_adj = pd.read_pickle(
                f'./第三买卖点/strategy_save/{U.py_name}_{U.first_start}_{U.last_end}/prices_adj_{U.py_name}_{U.first_start}_{U.latest_end}.pkl')
            prices_part = pd.read_pickle(
                f'./第三买卖点/strategy_save/{U.py_name}_{U.first_start}_{U.last_end}/prices_part_{U.py_name}_{U.first_start}_{U.latest_end}.pkl')
            prices_adj_high_level = pd.read_pickle(
                f'./第三买卖点/strategy_save/{U.py_name}_{U.first_start}_{U.last_end}/prices_adj_high_level_{U.py_name}_{U.first_start}_{U.latest_end}.pkl')
            prices_part_high_level = pd.read_pickle(
                f'./第三买卖点/strategy_save/{U.py_name}_{U.first_start}_{U.last_end}/prices_part_high_level_{U.py_name}_{U.first_start}_{U.latest_end}.pkl')

            pivot_latest_series = pd.read_pickle(
                f'./第三买卖点/strategy_save/{U.py_name}_{U.first_start}_{U.last_end}/pivot_latest_{U.py_name}_{U.first_start}_{U.latest_end}.pkl')
#             pivot_latest = pivot_latest_series.to_dict()
            pivot_latest  = strategy.dict_no_nat(pivot_latest_series)

            trading_point_series = pd.read_pickle(
                f'./第三买卖点/strategy_save/{U.py_name}_{U.first_start}_{U.last_end}/trading_point_level_3_{U.py_name}_{U.first_start}_{U.latest_end}.pkl')
#             trading_point_level_3 = trading_point_series.to_dict()
            trading_point_level_3  = strategy.dict_no_nat(trading_point_series)


            last_point_series = pd.read_pickle(
                f'./第三买卖点/strategy_save/{U.py_name}_{U.first_start}_{U.last_end}/last_trading_point_time_{U.py_name}_{U.first_start}_{U.latest_end}.pkl')
            
            U.last_trading_point_time = last_point_series.iloc[0]
            U.last_open = last_point_series.iloc[1]
            U.can_close = last_point_series.iloc[2]
            U.last_pivot = last_point_series.iloc[3]
#             print('\n','in_pivot:',U.last_pivot,'\n',last_point_series)


            U.pivot_df = pd.read_pickle(f'./第三买卖点/strategy_save/{U.py_name}_{U.first_start}_{U.last_end}/pivot_df_{U.py_name}_{U.first_start}_{U.latest_end}.pkl')
            U.three_point_df = pd.read_pickle(
                f'./第三买卖点/strategy_save/{U.py_name}_{U.first_start}_{U.last_end}/three_point_df_{U.py_name}_{U.first_start}_{U.latest_end}.pkl')


            prices_init = prices[prices['DATETIME'] < today + ' 09:45:00']
            for datetime in prices_init['DATETIME']:
                prices_latest = prices.loc[prices['DATETIME'] == datetime, :]
                prices_latest_high_level = prices_high_level.loc[prices_high_level['DATETIME'] == datetime, :]
                prices_adj, prices_part, prices_adj_high_level, prices_part_high_level, pivot_latest, trading_point_level_3 = \
                    three_point.three_point_latest_level2(prices_latest, prices_latest_high_level, prices_adj,
                                                          prices_part, \
                                                          prices_adj_high_level, prices_part_high_level, pivot_latest,
                                                          trading_point_level_3)

                U.pivot_df = U.pivot_df.append(pd.DataFrame({datetime.strftime('%Y-%m-%d %H:%M:%S'): pivot_latest}).T)
                if trading_point_level_3 != {}:
                    U.three_point_df = U.three_point_df.append(
                        pd.DataFrame({datetime.strftime('%Y-%m-%d %H:%M:%S'): trading_point_level_3}).T)




    elif today != U.start:
        # 承接同一产品中上一日的信息
        prices_adj = U.prices_adj
        prices_part = U.prices_part
        prices_adj_high_level = U.prices_adj_high_level
        prices_part_high_level = U.prices_part_high_level
        pivot_latest = U.pivot_latest
        trading_point_level_3 = U.trading_point_level_3

        prices_init = prices[prices['DATETIME'] < today + ' 09:45:00']
        for datetime in prices_init['DATETIME']:
            prices_latest = prices.loc[prices['DATETIME'] == datetime, :]
            prices_latest_high_level = prices_high_level.loc[prices_high_level['DATETIME'] == datetime, :]
            prices_adj, prices_part, prices_adj_high_level, prices_part_high_level, pivot_latest, trading_point_level_3 = \
                three_point.three_point_latest_level2(prices_latest, prices_latest_high_level, prices_adj, prices_part, \
                                                      prices_adj_high_level, prices_part_high_level, pivot_latest,
                                                      trading_point_level_3)
            U.pivot_df = U.pivot_df.append(pd.DataFrame({datetime.strftime('%Y-%m-%d %H:%M:%S'): pivot_latest}).T)
            if trading_point_level_3 != {}:
                U.three_point_df = U.three_point_df.append(
                    pd.DataFrame({datetime.strftime('%Y-%m-%d %H:%M:%S'): trading_point_level_3}).T)

    U.prices = prices
    U.prices_high_level = prices_high_level
    U.current_state = "WAITING"
#     U.per_size = per_size
    U.symbol = symbol  # .CFE
    U.symbols = symbols  # .CF

    U.prices_adj = prices_adj
    U.prices_part = prices_part
    U.prices_adj_high_level = prices_adj_high_level
    U.prices_part_high_level = prices_part_high_level
    U.pivot_latest = pivot_latest
    U.trading_point_level_3 = trading_point_level_3

    U.date = 'date_init'

    U.today = today