(6-4)量化选股程序

接下来将要讲解的实例是一个简单的量化选股脚本,通过调用Tushare获取股票数据,然后根据不同的选股模型来筛选符合条件的股票,并将结果保存到文件中。用户可以根据自己的需求选择不同的选股模型和参数。请注意,该代码仅供学习和参考,实际应用时需要根据自己的需求和风险管理进行进一步的开发和测试。

实例6-4量化选股程序(源码路径:daima/6/stock_online_dev.py

6.3.1  Tushare令牌初始化

编写Tushare令牌初始化函数Initial(),用于设置Tushare令牌,并初始化Tushare客户端。这是获取股票数据的前提步骤。具体实现代码如下所示。

def Initial():#初始化
    # 设置Tushare令牌
    token = ''
    ts.set_token(token)
    # 初始化Tushare客户端
    pro=ts.pro_api()
    return pro

6.3.2  辅助函数

编写辅助函数Stocklist()、Wait(n)和函数Menu(),其中函数Stocklist()用于获取A股市场的股票列表,包括股票代码等信息;Wait(n)是一个简单的辅助函数,用于等待一段时间,以控制访问频率,避免频繁访问Tushare API。函数Menu()用于显示用户菜单,让用户选择不同的选股模型。根据用户选择,它将调用不同的选股策略函数。具体实现代码如下所示。

def Stocklist():#获取股票列表

    sl=pro.stock_basic(exchange='',list_status='L',fields='ts_code')

    return sl

#    print(sl) #调试用



def Wait(n):

    i=0

    while i<n:

        i+=1



def Menu():

    print("请选择选股模型:")

    print("1.均线金叉模型")

    print("2.均线压制K线多时,K线站上均线模型")

    print("3.均线拐头模型")

    print("4.趋势模型")

    print("all:以上所有模型")

    choice=input()

    if choice=="1":

        freq=input("请输入均线周期:")

        mas=input("请输入短期均线:")

        mal=input("请输入长期均线:")

        n=input("请输入跨越的周期长度:")

        m=input("几天内金叉:")

        result=GoldenCross(freq,int(mas),int(mal),int(n),int(m))

        filename=freq+'cross'+mas+mal+'_'+n+'_'+m+'_'+now+'.txt' #文件名

        SaveResult(filename,result) #保存结果

    elif choice=="2":

        freq=input("请输入均线周期:")

        mas=input("请输入均线:")

        n=input("请输入跨越的周期长度:")

        m=input("K线在多长时间内站上均线:")

        result=Suppress(freq,int(mas),int(n),int(m))

        filename=freq+'suppress'+mas+'_'+n+"_"+m+'_'+now+'.txt' #文件名

        SaveResult(filename,result) #保存结果

    elif choice=='3':

        freq=input("请输入均线周期:")

        ma_s=input("请输入均线:")

        n=input("请输入跨越的周期长度:")

        m=input("均线拐头天数:")

        result=Bottom(freq,int(ma_s),int(n),int(m))

        filename=freq+'bottom'+ma_s+'_'+n+"_"+m+'_'+now+'.txt' #文件名

        SaveResult(filename,result) #保存结果

    elif choice=='4':

        freq=input("请输入均线周期:")

        ma_s=input("请输入均线:")

        n=input("请输入跨越的周期长度:")

        m=input("均线趋势上扬时间:")

        result=Suppress(freq,int(ma_s),int(n),int(m))

        filename=freq+'trend'+ma_s+'_'+n+"_"+m+'_'+now+'.txt' #文件名

        SaveResult(filename,result) #保存结果

    elif choice=='all':

        print("正在设定均线金叉模型参数:")

        freq1=input("请输入均线周期:")

        mas=input("请输入短期均线:")

        mal=input("请输入长期均线:")

        n1=input("请输入跨越的周期长度:")

        result=Cross(freq1,int(mas),int(mal),int(n1))

        print("正在设定均均线压制K线多时,K线站上均线模型参数:")

        freq2=input("请输入均线周期:")

        n2=input("请输入跨越的周期长度:")

        result=Suppress(freq2,int(n2))

6.3.3  保存结果

函数SaveResult(filename, result)用于将选股结果保存到指定的文件中,具体实现代码如下所示。

def SaveResult(filename,result):        
    with open ('G:/result/'+filename,'w') as f:
        for i in result:
            details=StockDetails(i)
            Wait(50000)
            for j in details:
                f.write(j)
            f.write('\n')
        f.close()

6.3.4  股票详情

函数StockDetails(ts_code)用于获取特定股票的详细信息,具体实现代码如下所示。

def StockDetails(ts_code):
    details=[] #记录股票详细信息
    tmp=pro.stock_basic(ts_code=ts_code) #获取DataFrame结构的信息
    for i in tmp.loc[0]: #遍历DataFrame中的label:0
        if i!=None:
            details.append(i+'\t')
    return details

6.3.5  选股策略

在本程序中提供了多种选股策略,每种选股策略均有独立的功能函数实现,具体说明如下:

  1. 函数Cross(freq, mas, mal, n):实现均线交叉选股策略。它会遍历股票列表,检查每支股票的短期均线是否在长期均线上方,并且在过去n个交易日内发生了金叉情况。
  2. 函数GoldenCross(freq, mas, mal, n, m):实现均线金叉选股策略。它会遍历股票列表,检查每支股票的短期均线是否在长期均线上方,并且在过去n个交易日内发生了金叉情况。此外,还要求金叉后的m天内价格上涨。
  3. 函数Suppress(freq, mas, n, m):实现K线站上均线选股策略。它会遍历股票列表,检查每支股票的K线是否站上了均线,并且在过去n个交易日内发生了这种情况。
  4. 函数Trend(freq, ma_s, n):实现单调递增选股策略。它会遍历股票列表,检查每支股票的均线是否在过去n个交易日内保持单调递增。
  5. 函数Bottom(freq, ma_s, n, m):实现均线拐点选股策略。它会遍历股票列表,检查每支股票的均线是否在过去n个交易日内发生了拐点,并且拐点后的m天内价格上涨。

上述选股函数的具体实现代码如下所示。

def Cross(freq,mas,mal,n): #均线交叉
    count=0 #计数
    total=len(sl['ts_code']) #总上市股票数
    result=[]
    for i in sl['ts_code']:
        os.system('clear')
        count+=1 #每判断一个股票,计数加1
        print('进度:'+str(count)+'/'+str(total)) #显示已判断股票数的比例
        print('正在比对:'+i) #调试用
        data=ts.pro_bar(ts_code=i,freq=freq,adj='qfq',start_date=previous,end_date=now,ma=[mas,mal])
        if data is None: #如果没有获取到任何数据,比如刚上市又还没上市的股票
            continue
        ma_s=data['ma'+str(mas)] #提取短期均线
        ma_l=data['ma'+str(mal)] #提取长期均线
        if len(ma_s)<n or len(ma_l)<n: #判断是否有空值
#            print(i+'上市时间过短')
            continue
        if (ma_s[0]-ma_l[0])>0 and (ma_s[n]-ma_l[n])<0:
            result.append(i)
#            print('捕获:'+data['ts_code'])
        if freq=='W':
            Wait(15000) #等待一段时长,防止频率过快,受限于帐号积分
        if freq=='M':
            Wait(5000000) #等待一段时长,防止频率过快,受限于帐号积分
#    print(ma13)
#    plt.plot(data['trade_date'],data['ma13'])
#    plt.plot(data['trade_date'],data['ma55'])
#    plt.show()
    return result

def GoldenCross(freq,mas,mal,n,m): #均线金叉
    count=0 #计数
    total=len(sl['ts_code']) #总上市股票数
    result=[]
    for i in sl['ts_code']:
        os.system('clear')
        count+=1 #每判断一个股票,计数加1
        print('进度:'+str(count)+'/'+str(total)) #显示已判断股票数的比例
        print('正在比对:'+i) #调试用
        data=ts.pro_bar(ts_code=i,freq=freq,adj='qfq',start_date=previous,end_date=now,ma=[mas,mal])
        if data is None: #如果没有获取到任何数据,比如刚上市又还没上市的股票
            continue
        ma_s=data['ma'+str(mas)] #提取短期均线
        ma_l=data['ma'+str(mal)] #提取长期均线
        if len(ma_s)<n or len(ma_l)<n: #判断是否有空值
            continue
        if ma_s[0]>ma_l[0]: #判断短期均线是不是在长期均线上方
            j=1
            crosspoint=0 #初始值为0,假设1天内出现金叉的情况
            while j<=n: #判断之前的收盘价是不是在均线下文,以此寻找刚启动的行情
                if ma_s[j]>ma_l[j]: #判断短期均线是否还在长期均线上方,不是则交叉点已经出现
                    crosspoint=j #记录金叉时的天数
                    j=j+1
                else:
                    if crosspoint<=m: #判断交叉点是否在要求的时间段里,是则继续判断
                        j+=1
                        if j==n: #交叉前的N天,短期均线都在长期均线下方,可以断定为金叉
                            result.append(i)
                    else:
                        break
        if freq=='W':
            Wait(20000) #等待一段时长,防止频率过快,受限于帐号积分
        if freq=='M':
            Wait(9000000) #等待一段时长,防止频率过快,受限于帐号积分
    return result

def Suppress(freq,mas,n,m): #K线站上均线模型
    count=0 #计数
    total=len(sl['ts_code']) #总上市股票数
    result=[]
    for i in sl['ts_code']:
        os.system('clear')
        count+=1 #每判断一个股票,计数加1
        print('Suppress进度:'+str(count)+'/'+str(total)) #显示已判断股票数的比例
        print('正在比对:'+i) #调试用
        data=ts.pro_bar(ts_code=i,freq=freq,adj='qfq',start_date=previous,end_date=now,ma=[mas])
#        data1=ts.pro_bar(ts_code=i,freq='D',adj='qfq',start_date=previous,end_date=now,ma=[mas])
#        data.to_csv('/tmp/online.csv')
#        break
        if data is None: #如果没有获取到任何数据,比如刚上市又还没上市的股票
            continue
        Wait(20000000) #等待一段时长,防止频率过快,受限于帐号积分
        close=data['close']
        ma=data['ma'+str(mas)]
        if len(close)<n or len(ma)<n: #判断是否有空值
            continue
        if close[0]>ma[0]: #判断最新收盘价是不是在均线上方
            j=1
            point=0
            while j<=n: #判断之前的收盘价是不是在均线下文,以此寻找刚启动的行情
                if close[j]>ma[j]: #判断K线是否还在长期均线上方,不是则突破压制
                    point=j #记录突破时的天数
                    j=j+1
                else:
                    if point==m: #判断突破是否在要求的时间段里,是则继续判断
                        if j==n: #突破前的N段时间内,都在均线下方,突破成立
                            result.append(i)
                        j+=1
                    else:
                        break
    return result

def Trend(freq,ma_s,n): #单调递增模型
    count=0 #计数
    total=len(sl['ts_code']) #总上市股票数
    result=[]
    for i in sl['ts_code']:
        os.system('clear')
        count+=1 #每判断一个股票,计数加1
        print('进度:'+str(count)+'/'+str(total)) #显示已判断股票数的比例
        print('正在比对:'+i) #调试用
        data=ts.pro_bar(ts_code=i,freq=freq,adj='qfq',start_date=previous,end_date=now,ma=[ma_s])
        if data is None: #如果没有获取到任何数据,比如刚上市又还没上市的股票
            continue
        ma=data['ma'+str(ma_s)]
        if len(ma)<n: #判断是否有空值
            continue
        j=0 #循环初始化
        while ma[j]>ma[j+1]:
            if j==n: #n天内,均线单调递增
                result.append(i)
                break
            j+=1
        if freq=='W':
            Wait(5000000) #等待一段时长,防止频率过快,受限于帐号积分
        if freq=='M':
            Wait(5000000) #等待一段时长,防止频率过快,受限于帐号积分
    return result
                

def Bottom(sl,freq,ma_s,n,m): #均线拐点
    global previous  # 使用全局的 previous 变量
    global q  # 使用全局的 q 变量
    count=0 #计数
    total=len(sl['ts_code']) #总上市股票数
    result=[]
    for i in sl['ts_code']:
        os.system('clear')
        count+=1 #每判断一个股票,计数加1
        print('Bottom进度:'+str(count)+'/'+str(total)) #显示已判断股票数的比例
        print('正在比对:'+i) #调试用
        data=ts.pro_bar(ts_code=i,freq=freq,adj='qfq',start_date=previous,end_date=now,ma=[ma_s])
        if data is None: #如果没有获取到任何数据,比如刚上市又还没上市的股票
            continue
        ma=data['ma'+str(ma_s)] #提取均线
        close=data['close'] #提取收盘价
        if len(ma)<n: #判断是否有空值
            continue
        if close[0]<ma[0]: #收盘价在均线上方,如在均线下文,则为弱势
            continue
        j=0 #初始化
        if ma[j]>ma[j+1]: #判断当前均值是否大于前一天,即均线拐头,如不是,则均线向下,不合要求,排除
            j=j+1
            while ma[j]>ma[j+1]: #向前递归,直到出现拐点
                j=j+1
            point=j #记录拐点
        else:
            continue
        if point==m: #拐点是否在要求的时间
            while ma[j]<=ma[j+1]: #向前递归,拐点前是否单调递减
                j=j+1
                if j==n: #直到规定的时间内,都是单调递减,则输出
                    result.append(i)
                    break #捕捉到致富代码,则退出循环,寻找下一个

        if freq=='D':
            Wait(5000000) #等待一段时长,防止频率过快,受限于帐号积分
        if freq=='W':
            Wait(500000) #等待一段时长,防止频率过快,受限于帐号积分
        if freq=='M':
            Wait(950000000) #等待一段时长,防止频率过快,受限于帐号积分
    q.put(result)
    return result

6.3.6  主程序

__main__ 部分是本实例的主程序部分,包含了代码的执行流程。首先初始化Tushare客户端,获取股票列表,然后根据用户菜单选择的不同选股策略调用相应的策略函数。在本例中,以 Bottom 为例进行演示。具体实现代码如下所示。

####主程序####

if __name__ == '__main__':

    pro=Initial() #初始化
    q=Queue()
    now=time.strftime("%Y%m%d") #当前日期
    #now='20201230'
    previous=int(now)-30000 #一年前的日期
    previous=str(previous) #转换成字符串
    sl=Stocklist() #股票列表
#    sl=sl[1:20] #调试用,限制股票数量以减短时间

#    global result

#    result=[]#全局变量,记录结果

    start=time.time()

    t1=Process(target=Bottom,args=(sl[100:200],'D',13,15,1))
    t1.start()
    t1.join()
    end=time.time()
    result=q.get()
    print(end-start)
    print(result)

#    Menu()
    #result=Cross('W',13,55,2) #调试用
    #result=Suppress('M',8,10) #调试用
    #result=GoldenCross('D',8,21,3,1) #调试用
    #result=Trend('W',55,50) #调试用
    #result=Bottom('D',55,10,2) #调试用
    #SaveResult('test',result) #调试用

另外,在主函数的注释掉的测试代码中,有一些示例代码用于测试不同的选股策略函数。这些示例代码以不同的策略调用函数,并且用于演示如何使用各个选股策略。以下是对被注释掉示例代码的说明:

  1. result=Cross('W',13,55,2):这行代码演示了如何使用Cross策略函数,其中参数包括选股的频率为周线('W'),短期均线周期为13,长期均线周期为55,跨越的周期长度为2。这个示例会检查过去的周线数据,查找金叉情况。
  2. result=Suppress('M',8,10):这行代码演示了如何使用Suppress策略函数,其中参数包括选股的频率为月线('M'),均线周期为8,跨越的周期长度为10。这个示例会检查过去的月线数据,查找K线是否站上均线的情况。
  3. result=GoldenCross('D',8,21,3,1):这行代码演示了如何使用GoldenCross策略函数,其中参数包括选股的频率为日线('D'),短期均线周期为8,长期均线周期为21,跨越的周期长度为3,金叉后的价格上涨天数为1。这个示例会检查过去的日线数据,查找金叉情况,并要求金叉后的第一天价格上涨。
  4. result=Trend('W',55,50):这行代码演示了如何使用Trend策略函数,其中参数包括选股的频率为周线('W'),均线周期为55,跨越的周期长度为50。这个示例会检查过去的周线数据,查找均线是否保持单调递增的情况。
  5. result=Bottom('D',55,10,2):这行代码演示了如何使用Bottom策略函数,其中参数包括选股的频率为日线('D'),均线周期为55,跨越的周期长度为10,均线拐头天数为2。这个示例会检查过去的日线数据,查找均线是否发生了拐点,并要求拐点后的价格上涨。

上述被注释掉的示例代码可以帮助用户了解如何使用不同的选股策略函数,并根据自己的需求进行自定义配置。在实际使用时,可以取消注释这些代码,并根据具体的选股需求进行调整和测试。

  • 22
    点赞
  • 22
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
通达信量化AI选股源码是针对量化投资领域设计的一种程序代码,旨在帮助投资者通过基于人工智能算法实现更有效的股票选股策略。该源码包含了通过大数据分析、机器学习和其他相关技术,对股票市场进行深入研究和分析的程序代码。 通达信量化AI选股源码的设计主要包括以下几个方面: 1. 数据获取和处理:源码通过数据接口获取各种与股票市场有关的数据,包括股票价格、交易量、财务数据等。然后对这些数据进行清洗、整理和预处理,以便后续的算法分析使用。 2. 特征工程和数据挖掘:源码通过各种特征工程技术,将原始数据转换成更有意义的特征,以提供给模型进行分析和预测。例如,可以通过计算技术指标、构造市场情绪指标等,来反映市场的不同方面。 3. 模型构建和训练:源码利用机器学习算法,构建股票选股模型。根据已有数据,选择适当的模型,比如支持向量机、随机森林或神经网络等,并通过对历史数据进行训练,使模型能够对未来的趋势进行预测。 4. 选股策略实施和回测:源码通过实施选股策略,即按照模型给出的预测结果,选择适合的股票进行投资。为了评估策略的有效性,源码还提供了回测功能,通过对历史数据的模拟交易,来评估策略的收益和风险。 通达信量化AI选股源码的使用需要一定的程和数据分析能力,同时也需要对股票市场和量化投资有一定的理解。通过对源码的理解和运用,投资者可以更加科学和系统地进行股票选股,提高投资效率和投资收益。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

码农三叔

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值