Use timing decorator for problems 21-40

This commit is contained in:
daniele 2023-06-07 18:17:42 +02:00
parent 634eb3f750
commit be5e97dfbb
Signed by: fuxino
GPG Key ID: 981A2B2A3BBF5514
20 changed files with 172 additions and 288 deletions

View File

@ -9,34 +9,28 @@
# Evaluate the sum of all the amicable numbers under 10000. # Evaluate the sum of all the amicable numbers under 10000.
from timeit import default_timer from projecteuler import sum_of_divisors, timing
from projecteuler import sum_of_divisors
def main(): @timing
start = default_timer() def p021():
sum_ = 0 sum_ = 0
for i in range(2, 10000): for i in range(2, 10000):
# Calculate the sum of proper divisors with the function # Calculate the sum of proper divisors with the function
# implemented in projecteuler.py. # implemented in projecteuler.py.
n = sum_of_divisors(i) n = sum_of_divisors(i)
# If i!=n and the sum of proper divisors of n=i,
# sum the pair of numbers and add it to the total. # If i!=n and the sum of proper divisors of n=i,
# sum the pair of numbers and add it to the total.
if i != n and sum_of_divisors(n) == i: if i != n and sum_of_divisors(n) == i:
sum_ = sum_ + i + n sum_ = sum_ + i + n
sum_ = sum_ // 2 sum_ = sum_ // 2
end = default_timer()
print('Project Euler, Problem 21') print('Project Euler, Problem 21')
print(f'Answer: {sum_}') print(f'Answer: {sum_}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p021()

View File

@ -9,12 +9,12 @@
# What is the total of all the name scores in the file? # What is the total of all the name scores in the file?
import sys import sys
from timeit import default_timer
from projecteuler import timing
def main(): @timing
start = default_timer() def p022():
try: try:
with open('p022_names.txt', 'r', encoding='utf-8') as fp: with open('p022_names.txt', 'r', encoding='utf-8') as fp:
names = list(fp.readline().replace('"', '').split(',')) names = list(fp.readline().replace('"', '').split(','))
@ -37,13 +37,9 @@ def main():
sum_ = sum_ + score sum_ = sum_ + score
i = i + 1 i = i + 1
end = default_timer()
print('Project Euler, Problem 22') print('Project Euler, Problem 22')
print(f'Answer: {sum_}') print(f'Answer: {sum_}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p022()

View File

@ -12,29 +12,26 @@
# #
# Find the sum of all the positive integers which cannot be written as the sum of two abundant numbers. # Find the sum of all the positive integers which cannot be written as the sum of two abundant numbers.
from timeit import default_timer from projecteuler import sum_of_divisors, timing
from projecteuler import sum_of_divisors
def is_abundant(n): def is_abundant(n):
return sum_of_divisors(n) > n return sum_of_divisors(n) > n
def main(): @timing
start = default_timer() def p023():
ab_nums = [False] * 28124 ab_nums = [False] * 28124
# Find all abundant numbers smaller than 28123. # Find all abundant numbers smaller than 28123.
for i in range(12, 28124): for i in range(12, 28124):
ab_nums[i] = is_abundant(i) ab_nums[i] = is_abundant(i)
sums = [False] * 28124 sums = [False] * 28124
# For every abundant number, sum every other abundant number greater # For every abundant number, sum every other abundant number greater
# than itself, until the sum exceeds 28123. Record that the resulting # than itself, until the sum exceeds 28123. Record that the resulting
# number is the sum of two abundant numbers. # number is the sum of two abundant numbers.
for i in range(1, 28123): for i in range(1, 28123):
if ab_nums[i]: if ab_nums[i]:
for j in range(i, 28123): for j in range(i, 28123):
@ -45,18 +42,14 @@ def main():
sum_ = 0 sum_ = 0
# Sum every number that was not found as a sum of two abundant numbers. # Sum every number that was not found as a sum of two abundant numbers.
for i in range(1, 28124): for i in range(1, 28124):
if not sums[i]: if not sums[i]:
sum_ = sum_ + i sum_ = sum_ + i
end = default_timer()
print('Project Euler, Problem 23') print('Project Euler, Problem 23')
print(f'Answer: {sum_}') print(f'Answer: {sum_}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p023()

View File

@ -8,23 +8,19 @@
# What is the millionth lexicographic permutation of the digits 0, 1, 2, 3, 4, 5, 6, 7, 8 and 9? # What is the millionth lexicographic permutation of the digits 0, 1, 2, 3, 4, 5, 6, 7, 8 and 9?
from itertools import permutations from itertools import permutations
from timeit import default_timer
from projecteuler import timing
def main(): @timing
start = default_timer() def p024():
# Generate all the permutations in lexicographic order and get the millionth one.
# Generate all the permutations in lexicographic order and get the millionth one.
perm = list(permutations('0123456789')) perm = list(permutations('0123456789'))
res = int(''.join(map(str, perm[999999]))) res = int(''.join(map(str, perm[999999])))
end = default_timer()
print('Project Euler, Problem 24') print('Project Euler, Problem 24')
print(f'Answer: {res}') print(f'Answer: {res}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p024()

View File

@ -21,32 +21,27 @@
# #
# What is the index of the first term in the Fibonacci sequence to contain 1000 digits? # What is the index of the first term in the Fibonacci sequence to contain 1000 digits?
from timeit import default_timer from projecteuler import timing
def main(): @timing
start = default_timer() def p025():
fib1 = 1 fib1 = 1
fib2 = 1 fib2 = 1
fibn = fib1 + fib2 fibn = fib1 + fib2
i = 3 i = 3
# Calculate the Fibonacci numbers until one with 1000 digits is found. # Calculate the Fibonacci numbers until one with 1000 digits is found.
while len(str(fibn)) < 1000: while len(str(fibn)) < 1000:
fib1 = fib2 fib1 = fib2
fib2 = fibn fib2 = fibn
fibn = fib1 + fib2 fibn = fib1 + fib2
i = i + 1 i = i + 1
end = default_timer()
print('Project Euler, Problem 25') print('Project Euler, Problem 25')
print(f'Answer: {i}') print(f'Answer: {i}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p025()

View File

@ -16,27 +16,24 @@
# #
# Find the value of d < 1000 for which 1/d contains the longest recurring cycle in its decimal fraction part. # Find the value of d < 1000 for which 1/d contains the longest recurring cycle in its decimal fraction part.
from timeit import default_timer from projecteuler import timing
def main(): @timing
start = default_timer() def p026():
max_ = 0 max_ = 0
for i in range(2, 1000): for i in range(2, 1000):
j = i j = i
# The repeating cycle of 1/(2^a*5^b*p^c*...) is equal to # The repeating cycle of 1/(2^a*5^b*p^c*...) is equal to that of 1/p^c*..., so factors 2 and 5 can be eliminated.
# that of 1/p^c*..., so factors 2 and 5 can be eliminated.
while j % 2 == 0 and j > 1: while j % 2 == 0 and j > 1:
j = j // 2 j = j // 2
while j % 5 == 0 and j > 1: while j % 5 == 0 and j > 1:
j = j // 5 j = j // 5
# If the denominator had only factors 2 and 5, there is no # If the denominator had only factors 2 and 5, there is no repeating cycle.
# repeating cycle.
if j == 1: if j == 1:
n = 0 n = 0
else: else:
@ -44,10 +41,10 @@ def main():
k = 9 k = 9
div = j div = j
# After eliminating factors 2s and 5s, the length of the repeating cycle # After eliminating factors 2s and 5s, the length of the repeating cycle
# of 1/d is the smallest n for which k=10^n-1/d is an integer. So we start # of 1/d is the smallest n for which k=10^n-1/d is an integer. So we start
# with k=9, then k=99, k=999 and so on until k is divisible by d. # with k=9, then k=99, k=999 and so on until k is divisible by d.
# The number of digits of k is the length of the repeating cycle. # The number of digits of k is the length of the repeating cycle.
while k % div != 0: while k % div != 0:
n = n + 1 n = n + 1
k = k * 10 k = k * 10
@ -57,13 +54,9 @@ def main():
max_ = n max_ = n
max_n = i max_n = i
end = default_timer()
print('Project Euler, Problem 26') print('Project Euler, Problem 26')
print(f'Answer: {max_n}') print(f'Answer: {max_n}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p026()

View File

@ -19,20 +19,17 @@
# #
# Find the product of the coefficients, a and b, for the quadratic expression that produces the maximum number of primes for consecutive values of n, starting with n=0. # Find the product of the coefficients, a and b, for the quadratic expression that produces the maximum number of primes for consecutive values of n, starting with n=0.
from timeit import default_timer from projecteuler import is_prime, timing
from projecteuler import is_prime
def main(): @timing
start = default_timer() def p027():
max_ = 0 max_ = 0
# Brute force approach, optimized by checking only values of b where b is prime. # Brute force approach, optimized by checking only values of b where b is prime.
for a in range(-999, 1000): for a in range(-999, 1000):
for b in range(2, 1001): for b in range(2, 1001):
# For n=0, n^2+an+b=b, so b must be prime. # For n=0, n^2+an+b=b, so b must be prime.
if is_prime(b): if is_prime(b):
n = 0 n = 0
count = 0 count = 0
@ -51,13 +48,9 @@ def main():
save_a = a save_a = a
save_b = b save_b = b
end = default_timer()
print('Project Euler, Problem 27') print('Project Euler, Problem 27')
print(f'Answer: {save_a * save_b}') print(f'Answer: {save_a * save_b}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p027()

View File

@ -12,12 +12,11 @@
# #
# What is the sum of the numbers on the diagonals in a 1001 by 1001 spiral formed in the same way? # What is the sum of the numbers on the diagonals in a 1001 by 1001 spiral formed in the same way?
from timeit import default_timer from projecteuler import timing
def main(): @timing
start = default_timer() def p028():
N = 1001 N = 1001
limit = N * N limit = N * N
@ -27,10 +26,10 @@ def main():
step = 0 step = 0
sum_ = 1 sum_ = 1
# Starting with the central 1, it's easy to see that the next four numbers in the diagonal # Starting with the central 1, it's easy to see that the next four numbers in the diagonal
# are 1+2, 1+2+2, 1+2+2+2 and 1+2+2+2+2, then for the next four number the step is increased # are 1+2, 1+2+2, 1+2+2+2 and 1+2+2+2+2, then for the next four number the step is increased
# by two, so from 9 to 9+4, 9+4+4 etc, for the next four number the step is again increased # by two, so from 9 to 9+4, 9+4+4 etc, for the next four number the step is again increased
# by two, and so on. We go on until the value is equal to N*N, with N=1001 for this problem. # by two, and so on. We go on until the value is equal to N*N, with N=1001 for this problem.
while j < limit: while j < limit:
if i == 0: if i == 0:
step = step + 2 step = step + 2
@ -38,13 +37,9 @@ def main():
sum_ = sum_ + j sum_ = sum_ + j
i = (i + 1) % 4 i = (i + 1) % 4
end = default_timer()
print('Project Euler, Problem 28') print('Project Euler, Problem 28')
print(f'Answer: {sum_}') print(f'Answer: {sum_}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p028()

View File

@ -13,23 +13,22 @@
# #
# How many distinct terms are in the sequence generated by ab for 2 ≤ a ≤ 100 and 2 ≤ b ≤ 100? # How many distinct terms are in the sequence generated by ab for 2 ≤ a ≤ 100 and 2 ≤ b ≤ 100?
from timeit import default_timer
from numpy import zeros from numpy import zeros
from projecteuler import timing
def main():
start = default_timer()
@timing
def p029():
powers = zeros(9801) powers = zeros(9801)
# Generate all the powers # Generate all the powers
for i in range(2, 101): for i in range(2, 101):
a = i a = i
for j in range(2, 101): for j in range(2, 101):
powers[(i-2)*99+j-2] = a ** j powers[(i-2)*99+j-2] = a ** j
# Sort the values and count the different values. # Sort the values and count the different values.
powers = list(powers) powers = list(powers)
powers.sort() powers.sort()
@ -39,13 +38,9 @@ def main():
if powers[i] != powers[i-1]: if powers[i] != powers[i-1]:
count = count + 1 count = count + 1
end = default_timer()
print('Project Euler, Problem 29') print('Project Euler, Problem 29')
print(f'Answer: {count}') print(f'Answer: {count}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p029()

View File

@ -12,17 +12,16 @@
# #
# Find the sum of all the numbers that can be written as the sum of fifth powers of their digits. # Find the sum of all the numbers that can be written as the sum of fifth powers of their digits.
from timeit import default_timer from projecteuler import timing
def main(): @timing
start = default_timer() def p030():
tot = 0 tot = 0
# Straightforward brute force approach. The limit is chosen considering that # Straightforward brute force approach. The limit is chosen considering that
# 6*9^5=354294, so no number larger than that can be expressed as sum # 6*9^5=354294, so no number larger than that can be expressed as sum
# of 5th power of its digits. # of 5th power of its digits.
for i in range(10, 354295): for i in range(10, 354295):
j = i j = i
sum_ = 0 sum_ = 0
@ -35,13 +34,9 @@ def main():
if sum_ == i: if sum_ == i:
tot = tot + i tot = tot + i
end = default_timer()
print('Project Euler, Problem 30') print('Project Euler, Problem 30')
print(f'Answer: {tot}') print(f'Answer: {tot}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p030()

View File

@ -10,7 +10,7 @@
# #
# How many different ways can £2 be made using any number of coins? # How many different ways can £2 be made using any number of coins?
from timeit import default_timer from projecteuler import timing
# Simple recursive function that tries every combination. # Simple recursive function that tries every combination.
@ -29,20 +29,15 @@ def count(coins, value, n, i):
return n return n
def main(): @timing
start = default_timer() def p031():
coins = [1, 2, 5, 10, 20, 50, 100, 200] coins = [1, 2, 5, 10, 20, 50, 100, 200]
n = count(coins, 0, 0, 0) n = count(coins, 0, 0, 0)
end = default_timer()
print('Project Euler, Problem 31') print('Project Euler, Problem 31')
print(f'Answer: {n}') print(f'Answer: {n}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p031()

View File

@ -9,34 +9,31 @@
# #
# HINT: Some products can be obtained in more than one way so be sure to only include it once in your sum. # HINT: Some products can be obtained in more than one way so be sure to only include it once in your sum.
from timeit import default_timer
import numpy as np import numpy as np
from numpy import zeros from numpy import zeros
from projecteuler import is_pandigital from projecteuler import is_pandigital, timing
def main(): @timing
start = default_timer() def p032():
n = 0 n = 0
# Initially I used a bigger array, but printing the resulting products # Initially I used a bigger array, but printing the resulting products
# shows that 10 values are sufficient. # shows that 10 values are sufficient.
products = zeros(10, int) products = zeros(10, int)
# To get a 1 to 9 pandigital concatenation of the two factors and product, # To get a 1 to 9 pandigital concatenation of the two factors and product,
# we need to multiply a 1 digit number times a 4 digit numbers (the biggest # we need to multiply a 1 digit number times a 4 digit numbers (the biggest
# one digit number 9 times the biggest 3 digit number 999 multiplied give # one digit number 9 times the biggest 3 digit number 999 multiplied give
# 8991 and the total digit count is 8, which is not enough), or a 2 digit # 8991 and the total digit count is 8, which is not enough), or a 2 digit
# number times a 3 digit number (the smallest two different 3 digits number, # number times a 3 digit number (the smallest two different 3 digits number,
# 100 and 101, multiplied give 10100, and the total digit count is 11, which # 100 and 101, multiplied give 10100, and the total digit count is 11, which
# is too many). The outer loop starts at 2 because 1 times any number gives # is too many). The outer loop starts at 2 because 1 times any number gives
# the same number, so its digit will be repeated and the result can't be # the same number, so its digit will be repeated and the result can't be
# pandigital. The nested loop starts from 1234 because it's the smallest # pandigital. The nested loop starts from 1234 because it's the smallest
# 4-digit number with no repeated digits, and it ends at 4987 because it's # 4-digit number with no repeated digits, and it ends at 4987 because it's
# the biggest number without repeated digits that multiplied by 2 gives a # the biggest number without repeated digits that multiplied by 2 gives a
# 4 digit number. # 4 digit number.
for i in range(2, 9): for i in range(2, 9):
for j in range(1234, 4987): for j in range(1234, 4987):
p = i * j p = i * j
@ -51,10 +48,10 @@ def main():
products[n] = p products[n] = p
n = n + 1 n = n + 1
# The outer loop starts at 12 because 10 has a 0 and 11 has two 1s, so # The outer loop starts at 12 because 10 has a 0 and 11 has two 1s, so
# the result can't be pandigital. The nested loop starts at 123 because # the result can't be pandigital. The nested loop starts at 123 because
# it's the smallest 3-digit number with no digit repetitions and ends at # it's the smallest 3-digit number with no digit repetitions and ends at
# 833, because 834*12 has 5 digits. # 833, because 834*12 has 5 digits.
for i in range(12, 99): for i in range(12, 99):
for j in range(123, 834): for j in range(123, 834):
p = i * j p = i * j
@ -70,7 +67,7 @@ def main():
products[n] = p products[n] = p
n = n + 1 n = n + 1
# Sort the found products to easily see if there are duplicates. # Sort the found products to easily see if there are duplicates.
products = np.sort(products[:n]) products = np.sort(products[:n])
sum_ = products[0] sum_ = products[0]
@ -79,13 +76,9 @@ def main():
if products[i] != products[i-1]: if products[i] != products[i-1]:
sum_ = sum_ + products[i] sum_ = sum_ + products[i]
end = default_timer()
print('Project Euler, Problem 32') print('Project Euler, Problem 32')
print(f'Answer: {sum_}') print(f'Answer: {sum_}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p032()

View File

@ -11,19 +11,19 @@
# If the product of these four fractions is given in its lowest common terms, find the value of the denominator. # If the product of these four fractions is given in its lowest common terms, find the value of the denominator.
from math import gcd from math import gcd
from timeit import default_timer
from projecteuler import timing
def main(): @timing
start = default_timer() def p033():
prod_n = 1 prod_n = 1
prod_d = 1 prod_d = 1
for i in range(11, 100): for i in range(11, 100):
for j in range(11, 100): for j in range(11, 100):
# If the example is non-trivial, check if cancelling the digit that's equal # If the example is non-trivial, check if cancelling the digit that's equal
# in numerator and denominator gives the same fraction. # in numerator and denominator gives the same fraction.
if i % 10 != 0 and j % 10 != 0 and\ if i % 10 != 0 and j % 10 != 0 and\
i != j and i % 10 == j // 10: i != j and i % 10 == j // 10:
n = i // 10 n = i // 10
@ -36,16 +36,12 @@ def main():
prod_n = prod_n * i prod_n = prod_n * i
prod_d = prod_d * j prod_d = prod_d * j
# Find the greater common divisor of the fraction found. # Find the greater common divisor of the fraction found.
div = gcd(prod_n, prod_d) div = gcd(prod_n, prod_d)
end = default_timer()
print('Project Euler, Problem 33') print('Project Euler, Problem 33')
print(f'Answer: {prod_d // div}') print(f'Answer: {prod_d // div}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p033()

View File

@ -7,23 +7,23 @@
# Note: as 1! = 1 and 2! = 2 are not sums they are not included. # Note: as 1! = 1 and 2! = 2 are not sums they are not included.
from math import factorial from math import factorial
from timeit import default_timer
from numpy import ones from numpy import ones
from projecteuler import timing
def main():
start = default_timer()
@timing
def p034():
a = 10 a = 10
sum_ = 0 sum_ = 0
factorials = ones(10, int) factorials = ones(10, int)
# Pre-calculate factorials of each digit from 0 to 9. # Pre-calculate factorials of each digit from 0 to 9.
for i in range(2, 10): for i in range(2, 10):
factorials[i] = factorial(i) factorials[i] = factorial(i)
# 9!*7<9999999, so 9999999 is certainly un upper bound. # 9!*7<9999999, so 9999999 is certainly un upper bound.
while a < 9999999: while a < 9999999:
b = a b = a
sum_f = 0 sum_f = 0
@ -38,13 +38,9 @@ def main():
a = a + 1 a = a + 1
end = default_timer()
print('Project Euler, Problem 34') print('Project Euler, Problem 34')
print(f'Answer: {sum_}') print(f'Answer: {sum_}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p034()

View File

@ -6,9 +6,7 @@
# #
# How many circular primes are there below one million? # How many circular primes are there below one million?
from timeit import default_timer from projecteuler import sieve, timing
from projecteuler import sieve
# Calculate all primes below one million, then check if they're circular. # Calculate all primes below one million, then check if they're circular.
@ -17,28 +15,28 @@ primes = sieve(N)
def is_circular_prime(n): def is_circular_prime(n):
# If n is not prime, it's obviously not a circular prime. # If n is not prime, it's obviously not a circular prime.
if primes[n] == 0: if primes[n] == 0:
return False return False
# The primes below 10 are circular primes. # The primes below 10 are circular primes.
if primes[n] == 1 and n < 10: if primes[n] == 1 and n < 10:
return True return True
tmp = n tmp = n
count = 0 count = 0
# If the number has one or more even digits, it can't be a circular prime. # If the number has one or more even digits, it can't be a circular prime.
# because at least one of the rotations will be even. # because at least one of the rotations will be even.
while tmp > 0: while tmp > 0:
if tmp % 2 == 0: if tmp % 2 == 0:
return False return False
# Count the number of digits. # Count the number of digits.
count = count + 1 count = count + 1
tmp = tmp // 10 tmp = tmp // 10
for _ in range(1, count): for _ in range(1, count):
# Generate rotations and check if they're prime. # Generate rotations and check if they're prime.
n = n % (10 ** (count - 1)) * 10 + n // (10 ** (count - 1)) n = n % (10 ** (count - 1)) * 10 + n // (10 ** (count - 1))
if primes[n] == 0: if primes[n] == 0:
@ -47,23 +45,18 @@ def is_circular_prime(n):
return True return True
def main(): @timing
start = default_timer() def p035():
count = 13 count = 13
# Calculate all primes below one million, then check if they're circular. # Calculate all primes below one million, then check if they're circular.
for i in range(101, N, 2): for i in range(101, N, 2):
if is_circular_prime(i): if is_circular_prime(i):
count = count + 1 count = count + 1
end = default_timer()
print('Project Euler, Problem 35') print('Project Euler, Problem 35')
print(f'Answer: {count}') print(f'Answer: {count}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p035()

View File

@ -6,32 +6,25 @@
# #
# (Please note that the palindromic number, in either base, may not include leading zeros.) # (Please note that the palindromic number, in either base, may not include leading zeros.)
from timeit import default_timer from projecteuler import is_palindrome, timing
from projecteuler import is_palindrome
def main(): @timing
start = default_timer() def p036():
N = 1000000 N = 1000000
sum_ = 0 sum_ = 0
# Brute force approach. For every number below 1 million, # Brute force approach. For every number below 1 million,
# check if they're palindrome in base 2 and 10 using the # check if they're palindrome in base 2 and 10 using the
# function implemented in projecteuler.c. # function implemented in projecteuler.c.
for i in range(1, N): for i in range(1, N):
if is_palindrome(i, 10) and is_palindrome(i, 2): if is_palindrome(i, 10) and is_palindrome(i, 2):
sum_ = sum_ + i sum_ = sum_ + i
end = default_timer()
print('Project Euler, Problem 36') print('Project Euler, Problem 36')
print(f'Answer: {sum_}') print(f'Answer: {sum_}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p036()

View File

@ -7,29 +7,26 @@
# #
# NOTE: 2, 3, 5, and 7 are not considered to be truncatable primes. # NOTE: 2, 3, 5, and 7 are not considered to be truncatable primes.
from timeit import default_timer from projecteuler import is_prime, timing
from projecteuler import is_prime
def is_tr_prime(n): def is_tr_prime(n):
# One-digit numbers and non-prime numbers are # One-digit numbers and non-prime numbers are
# not truncatable primes. # not truncatable primes.
if n < 11 or not is_prime(n): if n < 11 or not is_prime(n):
return False return False
tmp = n // 10 tmp = n // 10
# Remove one digit at a time from the right and check # Remove one digit at a time from the right and check
# if the resulting number is prime. Return 0 if it isn't. # if the resulting number is prime. Return 0 if it isn't.
while tmp > 0: while tmp > 0:
if not is_prime(tmp): if not is_prime(tmp):
return False return False
tmp = tmp // 10 tmp = tmp // 10
# Starting from the last digit, check if it's prime, then # Starting from the last digit, check if it's prime, then add back one digit at a time on the left and check if it
# add back one digit at a time on the left and check if it # is prime. Return 0 when it isn't.
# is prime. Return 0 when it isn't.
i = 10 i = 10
tmp = n % i tmp = n % i
@ -39,31 +36,26 @@ def is_tr_prime(n):
i = i * 10 i = i * 10
tmp = n % i tmp = n % i
# If it gets here, the number is truncatable prime. # If it gets here, the number is truncatable prime.
return True return True
def main(): @timing
start = default_timer() def p037():
i = 0 i = 0
n = 1 n = 1
sum_ = 0 sum_ = 0
# Check every number until 11 truncatable primes are found. # Check every number until 11 truncatable primes are found.
while i < 11: while i < 11:
if is_tr_prime(n): if is_tr_prime(n):
sum_ = sum_ + n sum_ = sum_ + n
i = i + 1 i = i + 1
n = n + 1 n = n + 1
end = default_timer()
print('Project Euler, Problem 37') print('Project Euler, Problem 37')
print(f'Answer: {sum_}') print(f'Answer: {sum_}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p037()

View File

@ -13,22 +13,19 @@
# #
# What is the largest 1 to 9 pandigital 9-digit number that can be formed as the concatenated product of an integer with (1,2, ... , n) where n > 1? # What is the largest 1 to 9 pandigital 9-digit number that can be formed as the concatenated product of an integer with (1,2, ... , n) where n > 1?
from timeit import default_timer from projecteuler import is_pandigital, timing
from projecteuler import is_pandigital
def main(): @timing
start = default_timer() def p038():
max_ = 0 max_ = 0
# A brute force approach is used, starting with 1 and multiplying # A brute force approach is used, starting with 1 and multiplying
# the number by 1, 2 etc., concatenating the results, checking if # the number by 1, 2 etc., concatenating the results, checking if
# it's 1 to 9 pandigital, and going to the next number when the # it's 1 to 9 pandigital, and going to the next number when the
# concatenated result is greater than the greatest 9 digit pandigital # concatenated result is greater than the greatest 9 digit pandigital
# value. The limit is set to 10000, since 1*10000=10000, 2*10000=20000 and # value. The limit is set to 10000, since 1*10000=10000, 2*10000=20000 and
# concatenating this two numbers a 10-digit number is obtained. # concatenating this two numbers a 10-digit number is obtained.
for i in range(1, 10000): for i in range(1, 10000):
n = 0 n = 0
j = 1 j = 1
@ -54,13 +51,9 @@ def main():
if n > 987654321: if n > 987654321:
break break
end = default_timer()
print('Project Euler, Problem 38') print('Project Euler, Problem 38')
print(f'Answer: {max_}') print(f'Answer: {max_}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p038()

View File

@ -6,18 +6,17 @@
# #
# For which value of p ≤ 1000, is the number of solutions maximised? # For which value of p ≤ 1000, is the number of solutions maximised?
from timeit import default_timer
from numpy import zeros from numpy import zeros
from projecteuler import timing
def main():
start = default_timer()
@timing
def p039():
max_ = 0 max_ = 0
savedc = zeros(1000, int) savedc = zeros(1000, int)
# Start with p=12 (the smallest pythagorean triplet is (3,4,5) and 3+4+5=12. # Start with p=12 (the smallest pythagorean triplet is (3,4,5) and 3+4+5=12.
for p in range(12, 1001): for p in range(12, 1001):
count = 0 count = 0
a = 0 a = 0
@ -25,16 +24,15 @@ def main():
c = 0 c = 0
m = 2 m = 2
# Generate pythagorean triplets. # Generate pythagorean triplets.
while m * m < p: while m * m < p:
for n in range(1, m): for n in range(1, m):
a = m * m - n * n a = m * m - n * n
b = 2 * m * n b = 2 * m * n
c = m * m + n * n c = m * m + n * n
# Increase counter if a+b+c=p and the triplet is new, # Increase counter if a+b+c=p and the triplet is new, then save the value of c to avoid counting the same
# then save the value of c to avoid counting the same # triplet more than once.
# triplet more than once.
if a + b + c == p and savedc[c] == 0: if a + b + c == p and savedc[c] == 0:
savedc[c] = 1 savedc[c] = 1
count = count + 1 count = count + 1
@ -44,14 +42,13 @@ def main():
tmpb = b tmpb = b
tmpc = c tmpc = c
# Check all the triplets obtained multiplying a, b and c # Check all the triplets obtained multiplying a, b and c for integer numbers, until the perimeters exceeds p.
# for integer numbers, until the perimeters exceeds p.
while tmpa + tmpb + tmpc < p: while tmpa + tmpb + tmpc < p:
tmpa = a * i tmpa = a * i
tmpb = b * i tmpb = b * i
tmpc = c * i tmpc = c * i
# Increase counter if the new a, b and c give a perimeter=p. # Increase counter if the new a, b and c give a perimeter=p.
if tmpa + tmpb + tmpc == p and savedc[tmpc] == 0: if tmpa + tmpb + tmpc == p and savedc[tmpc] == 0:
savedc[tmpc] = 1 savedc[tmpc] = 1
count = count + 1 count = count + 1
@ -60,19 +57,15 @@ def main():
m = m + 1 m = m + 1
# If the current value is greater than the maximum, # If the current value is greater than the maximum,
# save the new maximum and the value of p. # save the new maximum and the value of p.
if count > max_: if count > max_:
max_ = count max_ = count
res = p res = p
end = default_timer()
print('Project Euler, Problem 39') print('Project Euler, Problem 39')
print(f'Answer: {res}') print(f'Answer: {res}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p039()

View File

@ -10,21 +10,20 @@
# #
# d_1 × d_10 × d_100 × d_1000 × d_10000 × d_100000 × d_1000000 # d_1 × d_10 × d_100 × d_1000 × d_10000 × d_100000 × d_1000000
from timeit import default_timer
from numpy import zeros from numpy import zeros
from projecteuler import timing
def main():
start = default_timer()
@timing
def p040():
digits = zeros(1000005, int) digits = zeros(1000005, int)
i = 1 i = 1
value = 1 value = 1
# Loop on all numbers and put the digits in the right place # Loop on all numbers and put the digits in the right place
# in an array. Use modulo and division to get the digits # in an array. Use modulo and division to get the digits
# for numbers with more than one digit. # for numbers with more than one digit.
while i <= 1000000: while i <= 1000000:
if value < 10: if value < 10:
digits[i-1] = value digits[i-1] = value
@ -61,16 +60,12 @@ def main():
i = i + 6 i = i + 6
value = value + 1 value = value + 1
# Calculate the product. # Calculate the product.
n = digits[0] * digits[9] * digits[99] * digits[999] * digits[9999] * digits[99999] * digits[999999] n = digits[0] * digits[9] * digits[99] * digits[999] * digits[9999] * digits[99999] * digits[999999]
end = default_timer()
print('Project Euler, Problem 40') print('Project Euler, Problem 40')
print(f'Answer: {n}') print(f'Answer: {n}')
print(f'Elapsed time: {end - start:.9f} seconds')
if __name__ == '__main__': if __name__ == '__main__':
main() p040()