def prob_solution(a, x, b, y, c, z): num_pp = len(safe_primes) plus = True minus = True for i in range(num_ps_tests): #using safe primes ensures that the order of a and b modulo m is high, thus ensuring the probability of a^x+/-b^y=c^z is low, on the order of 1/m m = safe_primes[randrange(num_pp)] ax, by, cz = exp_bs(a, x, m), exp_bs(b, y, m), exp_bs(c, z, m) if plus and (ax + by) % m != cz: plus = False s = '-' if not minus: break if minus and (ax - by) % m != cz: minus = False s = '+' if not plus: break else: return [True, s] return [False, s]
def get_y(a, x, c, z, b, lrab, max_yc, b_gp): y_res_mod = [] max_ya = x * lrab max_y = max(max_ya, max_yc) p = 1 for pprime, pprime_sq, prime_sq_tot, prime_div in b_gp: #squared prime modulus ensures totient is divisible by prime ax, cz = exp_bs(a, x, pprime_sq), exp_bs(c, z, pprime_sq) d = (ax - cz) % pprime_sq if is_coprime(d, pprime_sq): y_sp = dlog_mod(b, d, pprime_sq, prime_sq_tot, prime_div) y_res_mod.append([y_sp, pprime]) p *= pprime if p > max_y: break else: print("Not enough primes to get y") #raise Error("Not enough primes to get y") return crt(y_res_mod)
def get_x(a, x, c, z, m, mf, t, lt): cz = exp_bs(c, z, m) f = exp_bs(a, t - x, m) g = exp_bs(a, lt, m) h = f * cz % m p = dlog(g, h, m, mf) x += p * lt return x
def beals_solver(b, y, c, z, max_a, max_x): """finds a and x s.t. a^x + b^y = c^z b, c mutually coprime""" crt_mod = 1 rep_crt = [] for pprime in prob_primes: pp_sq = pprime**2 t = pprime * (pprime - 1) by = exp_bs(b, y, pp_sq) cz = exp_bs(c, z, pp_sq) d = (cz - by) % pp_sq res_exp_pairs = [] for a in range(pp_sq): l = 0 if a == 0 else 1 for x in range(t): if l == d: re_pair = [a % pprime, x % pprime] if re_pair not in res_exp_pairs: res_exp_pairs.append(re_pair) else: l = l * a % pp_sq rep_crt.append([pprime, res_exp_pairs]) crt_mod *= pprime if crt_mod > max_a and crt_mod > max_x: break np = reduce(lambda a, b: a * len(b[1]), rep_crt, 1) #np = reduce(lambda a, b: a * b[0], rep_crt, 1) print("{!s} chinese remainder theorem permutations".format(np)) ax_pairs = crt_permutation(rep_crt, b, y, c, z) for axp in ax_pairs: a, x = axp print("\t{!s}^{!s} + {!s}^{!s} = {!s}^{!s}".format(a, x, b, y, c, z))
def prob_beals(min_xyz=3, min_abc=2): populate_pprimes_list() #minimum sum is x+y+z=3+3+3=9 and a+b+c=2+3+5=10 s = 19 while True: #print("Shell with sum {!s} completed!".format(s)) for a in range(min_abc, s + 1): s_1 = s - a for b in range(min_abc, s_1 + 1): s_2 = s_1 - b if b > a and is_coprime(a, b): for c in range(min_abc, s_2 + 1): s_3 = s_2 - c if is_coprime(a, c) and is_coprime(b, c): for x in range(min_xyz, s_3 + 1): s_4 = s_3 - x for y in range(min_xyz, s_4 + 1): z = s_4 - y if z >= min_xyz: for p in prob_primes: p_tot = p - 1 a_m, b_m, c_m = a % p, b % p, c % p x_m, y_m, z_m = x % p_tot, y % p_tot, z % p_tot a_x, b_y, c_z = exp_bs(a, x, p), exp_bs(b, y, p), exp_bs(c, z, p) if (a_x + b_y) % p != c_z: break else: print("{!s}^{!s} + {!s}^{!s} = {!s}^{!s}".format(a, x, b, y, c, z)) s += 1
def miller_rabin_test(n, pci=prob_comp_ind): nm = n - 1 d = nm s = 0 #number of tests required to establish probable primeness k = math.ceil(-math.log(pci, 4)) while d % 2 == 0: s += 1 d //= 2 sm = s - 1 for i in range(k): a = randrange(2, nm) x = exp_bs(a, d, n) if x == 1 or x == nm: continue else: for j in range(sm): x = x**2 % n #early stopping x=1 for all powers of s > j if x == 1: return False #early stopping, the condition we're trying to prevent if x == nm: break else: return False return True