fork(2) download
  1. wheel = [2,4,2,4,6,2,6,4,2,4,6,6,2,6,4,2,6,4,6,8,4,2,4,2,
  2. 4,8,6,4,6,2,4,6,2,6,6,4,2,4,6,2,6,4,2,4,2,10,2,10]
  3. wsize = 48
  4.  
  5. def primes():
  6. yield from (2, 3, 5, 7)
  7. yield from wsieve()
  8.  
  9. def wsieve(): # wheel-sieve, by Will Ness. cf. ideone.com/WFv4f
  10. yield 11 # cf. http://stackoverflow.com/a/10733621/849891
  11. mults = {} # http://stackoverflow.com/a/19391111/849891
  12. ps = wsieve() # base primes
  13. p = next(ps) # 11
  14. psq = p*p # 121
  15. c = 11 # the last Candidate
  16. i = 0 # position on the wheel for next c: 11+2 =: 13
  17. cbase = 11 # base coprimes stream, to gen the mults for primes in it
  18. ibase = 0 # position on wheel for cbase==p
  19. while True:
  20. c += wheel[i] # next candidate from coprimes
  21. i = (i+1) % wsize # on the wheel
  22. if c not in mults: # c's not a multiple of any base prime:
  23. if c < psq: # hence, a prime
  24. yield c ; continue # ; or
  25. else: # (c==psq) # is the next base prime's square:
  26. while not cbase == p: # skip on base coprimes until
  27. cbase += wheel[ibase] # the base prime from rec supply
  28. ibase = (ibase+1) % wsize
  29. # map (p*) $ scanl (+) p (d:w) =
  30. # = scanl (\c d->c+p*d) (p*p) (d:w)
  31. # add(mults, c, ibase, p) # add NEXT mult of p after c==psq
  32. j = ibase ; pbase = p # go from ibase on the wheel
  33. p = next(ps) ; psq = p*p
  34. else: # `c` is a mult of prev-seen base prime:
  35. (j,pbase) = mults.pop(c)
  36. # add(mults, c, j, pbase) # add NEXT mult of pbase after c
  37. m = c + pbase*wheel[j] ; j = (j+1) % wsize
  38. while m in mults:
  39. m += pbase*wheel[j] ; j = (j+1) % wsize
  40. mults[m] = (j,pbase) # into the mults dict
  41.  
  42. import itertools # 100K 0.42s-8.7MB 800K 4.00s-8.7MB n^1.1
  43. # 200K 0.88s-8.7MB 1M 5.10s-8.7MB
  44. if True: # 400K 1.88s-8.7MB n^1.1 2M 10.88s-8.7MB n^1.1
  45. n = 800000
  46. print(n)
  47. print( list( itertools.islice( (p for p in primes() ), n-1, n+1)))
Success #stdin #stdout 3.9s 8688KB
stdin
Standard input is empty
stdout
800000
[12195257, 12195263]