from datetime import * def initialize(context): g.choicenum = 7 #預選小市值股票數 g.days = 0 # 計時器 g.period = 13 #調倉頻率 g.openorder=[] #未能成功清倉的股票名 def before_trading_start(context): # 今天是否運行 g.run_today = g.days % g.period == 0 if g.run_today: # 設置滬深兩市全部股票爲股票池 scu0 = get_index_stocks('000001.XSHG') scu3 = get_index_stocks('399001.XSHE') scu = scu0+scu3 #移除ST edf = get_extras('is_st', scu, start_date = context.current_dt, end_date=context.current_dt) glist = [] for sname in edf: if not edf.ix[0,sname]: glist.append(sname) set_universe(glist) #每一個交易日結束運行 def after_trading_end(context): #獲得當前未完成訂單 orders = get_open_orders() #循環,撤銷訂單 for _order in orders.values(): cancel_order(_order) #cancel_order(_order.order_id) pass def handle_data(context, data): # 調倉日交易 if g.run_today: # 天天只運行一次 g.run_today = False # 前個收盤日時的市值 ldate = context.current_dt+timedelta(days=-1) lastdate = ldate.strftime("%Y-%m-%d") # 選出低市值的股票,buylist df = get_fundamentals(query( valuation.code,valuation.market_cap ).filter( valuation.code.in_(context.universe) ).order_by( valuation.market_cap.asc() ).limit(g.choicenum*2), date=lastdate ).dropna() buylist = list(df.code) # 目前持倉中不在buylist中的股票,清倉 for stock in context.portfolio.positions: if stock not in buylist[:g.choicenum]: #停牌或跌停沒法出售 order_target(stock,0) # 等權重買入buylist中的股票, 現金和股票市值總得計算 position_per_stk = context.portfolio.portfolio_value/g.choicenum count= 0 for stock in buylist: if not (data[stock].isnan() or data[stock].paused): count += 1 df = get_price(stock, start_date=context.current_dt.strftime("%Y-%m-%d 09:30:00"), end_date=context.current_dt.strftime("%Y-%m-%d 09:30:00"), frequency="1m", fields=['price']) price = df.ix[0,'price'] if stock in context.portfolio.positions: pos = context.portfolio.positions[stock] stk = pos.amount*pos.price if stk<position_per_stk: buycash = min(context.portfolio.cash, position_per_stk-stk) buynum = int(buycash/price/100)*100 if buynum>0: order(stock, buynum) else: #超過平均市值忽略 print "ignore %s"%stock pass else: #新入列 buycash = min(context.portfolio.cash, position_per_stk) amount = int(buycash/price/100)*100 if amount>0: order(stock, amount) else: print stock,data[stock].isnan(),data[stock].paused if count >= g.choicenum: break # 天數加一 g.days += 1