예제 #1
0
def min_divisors_sum(n):
    """min(d1 + d2 + ... + dk - k | d1 * d2 * ... * dk == n)"""
    if n not in min_divisors_sum_save:
        s = 0
        for p, k in factorize(n).iteritems():
            s += (p - 1) * k
        min_divisors_sum_save[n] = s
    return min_divisors_sum_save[n]
예제 #2
0
def num_factors(n, a, b, c, d):
    #print n, (a, b, c, d), (2 ** a * 5 ** b , 2 ** c * 5 ** d) 
    f = factorize(2 ** a * 5 ** b + 2 ** c * 5 ** d)
    #print 2 ** a * 5 ** b + 2 ** c + 5 ** d, f
    f[2] = (f[2] if f.has_key(2) else 0) + n - a - c
    f[5] = (f[5] if f.has_key(5) else 0) + n - b - d
    #print f
    return prod([v + 1 for v in f.itervalues()])
예제 #3
0
def factors(n, P):  # assuming n > 1
    '''Return set of factors of n that are co-prime with 2 and 5. P = prime list to use for factorization.'''
    # print 'n', n
    d = factorize(n, P)
    d_filtered = [(k, v) for k, v in d.iteritems() if k != 2 and k != 5] if d else []
    if not d_filtered: return set([1, n] if n != 2 and n != 5 else [1])
    keys, values, m = [f[0] for f in d_filtered], [f[1] for f in d_filtered], len(d_filtered)
    # print 'n', n, 'd', d, d_filtered, keys, values, 'm', m
    # print list(it.product(*(xrange(v + 1) for v in values)))
    return set([np.prod([keys[i] ** combo[i] for i in xrange(m)]) for combo in it.product(*(xrange(v + 1) for v in values))])
예제 #4
0
def sum_4p3(n):
    """Sum of all the numbers <= n with prime divs 2, 4k + 3."""
    if n >= len(sum_4p3_save):
        for k in range(len(sum_4p3_save), n + 1):
            no_4k1 = True
            for p, _ in factorize(k).iteritems():
                if p % 4 == 1:
                    no_4k1 = False
                    break
        if no_4k1: sum_4p3_save.append(sum_4p3_save[-1] + k)
        else: sum_4p3_save.append(sum_4p3_save[-1])
    return sum_4p3_save[n]
예제 #5
0
def first_in_seq(L, limit=None):
    '''Will run indefinitely if a sequence of size L does not exist.'''
    y = 1
    for x in (it.count(2) if limit is None else xrange(2, limit + 1)):
        if x % 10000 == 0:
            print x
        # if is_not_admissible(x, L):
        if len(set(factorize(x).keys())) != L:
            y = x
        if x - y == L:  # L consecutive successes
            return y + 1
    return None
예제 #6
0
def divisors(n):
    f = factorize(n).items()
    d = 1
    p = [0] * len(f)
    while True:
        yield d
        i = 0
        while i < len(f) and p[i] == f[i][1]:
            p[i] = 0
            d //= f[i][0] ** f[i][1]
            i += 1
            if i >= len(f): break
            p[i] += 1
        d *= f[i][0]
예제 #7
0
def min_n_above(S):
    s = 2 * S + 1
    m = int(ceil(log(s) / log(3)))
    p = primes('first', m)
    fac, n, f = dict((x, factorize(x)) for x in xrange(1, p[-1])), prod([long(x) for x in p]), dict((x, 1) for x in p)
    while p.size:
        found, f0 = False, f.copy()
        del f0[p[-1]]
        for t in xrange(1, p[-1]):
            ft = f0.copy()
            for k, v in fac[t].iteritems(): ft[k] += v
            if prod([2 * k + 1 for k in ft.itervalues()]) > s:
                found, n, f, p = True, (n / p[-1]) * t, ft, p[:-1]
                break
        if not found: break
    return n
예제 #8
0
def prog_sq(N):
    '''Return the set of progressive perfect squares <= N.'''
    result = set([])
    for q in xrange(2, int((N / 2.) ** (2. / 3.)) + 1):
        factors, Q = factorize(q), q * q * q
        P, c_max = map(long, factors.keys()), min(int(Q ** 0.5), q)
        # print 'q', q, 'q^3', Q, factors, 'c_max', c_max
        for K in product(*(xrange(3 * k + 1) for k in factors.itervalues())):
            c = prod([p ** k for p, k in zip(P, K)])
            if c <= c_max:
                # print '\t', c, Q / c
                a2 = c + Q / c
                if a2 <= N and is_int(a2 ** 0.5):
                    # print 'Found', 'q', q, 'q^3', Q, 'c', c, 'd', Q / c, 'n', a2, ' =', int(a2 ** 0.5), '^ 2'
                    d = (a2 - c) / q
                    print 'Found', 'n', a2, ' =', int(a2 ** 0.5), '^ 2 =', 'q', q, 'd', d, 'r', c, 'd**0.5', d ** 0.5, '(d/2)**0.5', (d / 2.) ** 0.5 
                    result.add(a2)
    return result
예제 #9
0
def min_n(S):
    '''Brute-force, not terribly efficient. See Problem 110 for a better method.'''
    s = 2 * S + 1
    return dropwhile(prod(lambda n: prod([2 * k + 1 for k in factorize(n).itervalues()]) <= s), count(2)).next()
예제 #10
0
'''
============================================================
http://projecteuler.net/problem=187

A composite is a number containing at least two prime factors. For example, 15 = 3  5; 9 = 3  3; 12 = 2  2  3.

There are ten composites below thirty containing precisely two, not necessarily distinct, prime factors: 4, 6, 9, 10, 14, 15, 21, 22, 25, 26.

How many composite integers, n  108, have precisely two, not necessarily distinct, prime factors?
============================================================
'''
from problem007 import primes
from itertools import takewhile
from math import ceil
from problem012 import factorize

def num_comp2(N):
    p_limit = int(ceil(N - 1) ** 0.5)
    P = primes('lt', int(ceil(N - 1) * 0.5) + 1)  # Sorted ascending
    return sum(sum(1 for _ in takewhile(lambda q: q <= q_limit, P[k:])) 
               for (k, q_limit) in ((k, N / p) for k, p in enumerate(takewhile(lambda p: p <= p_limit, P)))) 

num_comp2_bf = lambda N: sum(1 for (_, f) in ((n, factorize(n)) for n in xrange(2, N))  # @UnusedVariable
                             if (len(f) == 2 and f.values() == [1, 1]) or
                             (len(f) == 1 and f.values() == [2]))
    
if __name__ == "__main__":
    print num_comp2(10 ** 8)
예제 #11
0
def sum_roots_of_unity(n, k):
    '''Sum of all kth-order roots of unit of n using the Chinese Remainder Theorem.''' 
    f = map(int, [p ** l for p, l in factorize(n).iteritems()])
    return sum(crt(zip(r, f)) for r in product(*(filter(lambda x: pow(x, k, p) == 1, xrange(1, p)) for p in f)))
예제 #12
0
def other_factor(k, factors):
    '''Does k have other primes factors than the list ''factors''?'''
    i, l = 0, len(factors)
    while i < l and k > 1:
        if k % factors[i] == 0: k /= factors[i]
        else: i += 1
    return k > 1

def sum_using_other_factor(max_prime):
    s = 0
    for p in islice(primes('lt', max_prime), 3, 100000000):
        a = A(p)
        other_fac = other_factor(a, ten_factors)
        if other_fac:
            s += p 
        print p, a, other_fac, s
    return s + 10  # 10=2+3+5 = boundary case

def sum_using_max_n(max_prime, n=16):
    k = 10 ** n
    return sum(p for p in primes('lt', max_prime) if pow(10, k, int(9 * p)) != 1)

sum_mine = lambda max_prime: 10 + sum(p for (p, _) in ifilter(lambda (_, a): not (factorize(a).keys() <= ten_factors), ((p, A(p)) for p in primes('lt', max_prime) if p != 2 and p != 5)))
    
if __name__ == "__main__":
    N = 10 ** 5
    print sum_using_max_n(N)
    print sum_using_other_factor(N)
    print sum_mine(N)
예제 #13
0
from problem007 import primes
from itertools import takewhile
from problem012 import factorize

'''A dynamic programming solution.'''
class HammingCounter(object):
    def __init__(self, max_k): self.h, self.p = {}, primes('lt', max_k + 1)
    def H_of_prime(self, n, k): return self.H(n, sum(1 for _ in takewhile(lambda p:p <= k, self.p)) - 1)
    def H(self, n, k): return self.h.setdefault((n, k), self._H(n, k))
    def _H(self, n, k):
        if n == 1 or k < 0: return 1
        h, km, p = 0, k - 1, self.p[k]
        while n:
            h += self.H(n, km)
            n /= p
        return h

num_hamming = lambda n, k: HammingCounter(k).H_of_prime(n, k)

'''Brute-force counting.'''
num_hamming_bf = lambda n, k: sum(1 for x in xrange(2, n + 1) if max(factorize(x).iterkeys()) <= k) + 1
hamming_bf = lambda n, k: [1] + [x for x in xrange(2, n + 1) if max(factorize(x).iterkeys()) <= k]
    
if __name__ == "__main__":
    print hamming_bf(15, 5)
    print num_hamming(15, 5), num_hamming_bf(15, 5)
    print num_hamming(10000, 100), num_hamming_bf(10000, 100)
    print num_hamming(10 ** 8, 5)
    print num_hamming(10 ** 9, 100)
    print num_hamming(10 ** 10, 100)