查找范围{k}中的k-prime数量

时间:2018-01-26 00:45:03

标签: python primes simplify

使用给定参数k,start,nd写函数count_Kprimes,返回start(包括)和end(包括)之间的k-prime列表。

这是我的尝试:

def count_Kprimes(k, start, nd):
  ls = []
  for x in range(start, nd + 1):
    y = x
    l = []
    for i in range(2, x + 1):
      while y % i == 0:
        l.append(i)
        y /= i
    if len(l) == k:
      ls.append(x)
  return ls

但是,我的代码需要花费太多时间来处理,我只想简单地编写代码。怎么做到呢?非常感谢你!

此任务取自Codewar

1 个答案:

答案 0 :(得分:0)

嗯,无论如何我很乐意解决这个问题。这是一个基于数组逻辑的解决方案

def count_Kprimes(k, start, nd):    
    x = np.arange(start, nd + 1, dtype=np.float)

    # divs will contain all divisors (plus one extra column)
    divs = np.ones((x.size, k + 1))

    # we have to loop only nd / 2^(k-1) to get all divisors
    for i in range(2, int(nd / 2 ** (k - 1)) + 1):

        # but each possible divisor "i" may occur up to k times
        # we loop until k+1 to catch also number that exceed our target,
        # so we can discard them later
        for j in range(1, k + 2):            

            # check for each row (dimension 0) if i is a divisor            
            # then set the first zero-value in dimension 1 to be this divisor                    
            d = np.prod(divs, axis=1)            
            divs[[[np.rint(x/d/i)==x/d/i][0],np.argmin(divs[np.rint(x/d/i)==x/d/i], axis=1)]] = i            

    # The correct result we're looking for is each row that has exactly
    # k values != 1 (which equals to exactly one "1" per row)
    indices = np.apply_along_axis(lambda x: x[x==1].size == 1, 1, divs)

    for val, d in zip(x[indices], divs[indices]):
        print "{} = {}".format(int(val), " * ".join([str(int(_)) for _ in d[:-1]]))

count_Kprimes(3, 1, 100)

返回

8 = 2 * 2 * 2
12 = 2 * 2 * 3
18 = 2 * 3 * 3
20 = 2 * 2 * 5
27 = 3 * 3 * 3
28 = 2 * 2 * 7
30 = 2 * 3 * 5
42 = 2 * 3 * 7
44 = 2 * 2 * 11
45 = 3 * 3 * 5
50 = 2 * 5 * 5
52 = 2 * 2 * 13
63 = 3 * 3 * 7
66 = 2 * 3 * 11
68 = 2 * 2 * 17
70 = 2 * 5 * 7
75 = 3 * 5 * 5
76 = 2 * 2 * 19
78 = 2 * 3 * 13
92 = 2 * 2 * 23
98 = 2 * 7 * 7
99 = 3 * 3 * 11