既然你以前用过C++。而且写的方式也很像C。那就可以直接用numba优化一下。没有用多线程或者是多进程。
我试了一下,iend=10是1.5s, iend=34, 大约是30分钟。
#双色球所有号码历次中奖查询代码
import time
import numba
import numpy as np
filename="i:/ssq.txt中存储的是双色球历次中奖号码,形式每行如01182630313303,六个红球一个蓝球号码,共1533行
start=time.time()
with open(filename) as file_object:
numstrings = file_object.readlines()
#---把中奖号码存在这个数组里
nums = np.zeros((len(numstrings), 7), dtype=np.int32)
for i,s in enumerate(numstrings):
nums[i,:] = [int(s[0:2]),int(s[2:4]),int(s[4:6]),int(s[6:8]),int(s[8:10]),int(s[10:12]),int(s[12:14])]
@numba.njit #---用numba jit 优化,不用python
def run(nums):
iend = 10 # iend调试用,iend=34时为实际情况,共17721088种可能,调试时iend=10,共1344种可能
length = len(nums)
n = np.zeros(7, dtype=np.int32) #
for i0 in range(1,17):
for i1 in range(1,iend-5):
for i2 in range(i1+1,iend-4):
for i3 in range(i2+1,iend-3):
for i4 in range(i3+1,iend-2):
for i5 in range(i4+1,iend-1):
for i6 in range(i5+1,iend):
#构建循环框架,i0为蓝球,i1-i6为红球
#在我的破机子上,循环一遍17721088次,每次只计数加1,用时就到了4.698s
#然后是对每一个i0-i6,判断在1533期中,总共中了几个一等奖到六等奖,
n[0], n[1], n[2], n[3], n[4], n[5], n[6] = i1,i2,i3,i4,i5,i6,i0 #---快速赋值,避免用tuple
#n = i1,i2,i3,i4,i5,i6,i0
j1,j2,j3,j4,j5,j6 = 0,0,0,0,0,0 #---原程序忘记加了
for s in range(length):
ired,iblue=0,0
# s1,s2,s3,s4,s5,s6,s0=nums[s,:]
for i in range(0,6):
#if(n[i] in (s1,s2,s3,s4,s5,s6)):
if(n[i] == nums[s,0]) or (n[i] == nums[s,1]) or (n[i] == nums[s,2]) or (n[i] == nums[s,3]) or (n[i] == nums[s,4]) or (n[i] == nums[s,5]):
ired += 1
# if( i0 == s0 ):
if( i0 == nums[s,6]):
iblue += 1
if((ired,iblue)==(6,1)):
j1 += 1
if((ired,iblue)==(6,0)):
j2 += 1
if((ired,iblue)==(5,1)):
j3 += 1
if((ired,iblue)==(5,0))or((ired,iblue)==(4,1)):
j4 += 1
if((ired,iblue)==(4,0))or((ired,iblue)==(3,1)):
j5 += 1
if((ired,iblue)==(2,1))or((ired,iblue)==(1,1))or((ired,iblue)==(0,1)):
j6 += 1
print(n,' ',j1,j2,j3,j4,j5,j6)
result = run(nums)
end=time.time()
print(f"Running time %s seconds"%(end-start))
【 在 Eggcai 的大作中提到: 】
: 20年前用的是C++,现在学习python,写一个程序,算双色球中奖的。列举所有C(6,33)*16=17721088种可能的号码,从有据可查到现在的1500多期开奖,每个号码能够中多少个一等奖,多少个二等奖到六等奖。
: 程序写出来了,但是运行时间不能接受,求优化代码
: #双色球所有号码历次中奖查询代码
: ...................
--
FROM 123.118.98.*