def spectrum(n, field): q = field.order p = field.char # (1) eps = 1 if n % 2 == 0 else e a1 = [(q ** n - eps) // (q - e)] # (2) a2 = SemisimpleElements(q, n, min_length=2, sign=e) # (3) a3 = [] k = 1 d = gcd(n, q - e) while True: n1 = n - p ** (k - 1) - 1 if n1 < 1: break eps = 1 if n1 % 2 == 0 else e a3.append(p ** k * (q ** n1 - eps) / gcd(d, n1)) k += 1 # (4) a4 = MixedElements(q, n, lambda k: p ** (k - 1) + 1, lambda k: p ** k, min_length=2, sign=e) # (5) k = numeric.get_exponent(n - 1, p) a5 = [] if k is None else [p * (n - 1) * d] # (6) a6 = [p * gcd(2, q - 1) * (q + e)] if n == 4 else [] return itertools.chain(a1, a2, a3, a4, a5, a6)
def _omega_pm_spectrum_odd_c(n: int, field: 'Field', sign: int) -> Iterable[int]: """Spectra of Omega^e_{2n}(q) for odd q. Based on [1, Corollary 8] and [3, Lemma 2.3] Point 3 of [1, Corollary 8] contains an error that was corrected in [3, Lemma 2.3] """ n //= 2 q = field.order p = field.char def nk(k): return (p ** (k - 1) + 3) // 2 # (1) a1 = [(q ** n - sign) // 2] # (2) a2 = SemisimpleElements(q, n, min_length=2, parity=sign) # (3) a3 = [] k = 1 while True: n_k = nk(k) if n_k >= n: break for delta in [1, -1]: dk = gcd(4, q ** n_k - sign * delta) // 2 a3.append( p ** k * lcm( dk, (q**(n - n_k) - delta) // dk ) ) k += 1 # (4) a4 = MixedElements(q, n, nk, lambda k: p ** k, min_length=2) # (5) a5 = [] for elem in SemisimpleElements(q, n - 2, min_length=2, parity=sign): a5.append(elem.lcm(SpectraElement(p, q, [1], [-1]))) a5.append(elem.lcm(SpectraElement(p, q, [1], [1]))) # (6) t = (q ** (n - 2) - sign) // 2 a6 = [p * lcm(q - 1, t), p * lcm(q + 1, t)] # (7) k = numeric.get_exponent(2 * n - 3, p) a7 = [] if k is None else [p * (2 * n - 3) * gcd(4, q ** n - sign) // 2] # (8) a8 = [p * (q * q - 1), p * (q * q + 1)] if n == 4 and sign == 1 else [] # (9) a9 = [9 * (q - 1), 9 * (q + 1)] if n == 4 and p == 3 and sign == 1 else [] return itertools.chain(a1, a2, a3, a4, a5, a6, a7, a8, a9)
def spectrum(n: int, field: 'Field') -> Iterable[int]: q = field.order p = field.char # (1) eps = 1 if n % 2 == 0 else e a1 = [(q ** n - eps) // (q - e)] # (2) a2 = SemisimpleElements(q, n, min_length=2, sign=e) # (3) a3 = [] k = 1 d = gcd(n, q - e) while True: n1 = n - p ** (k - 1) - 1 if n1 < 1: break eps = 1 if n1 % 2 == 0 else e a3.append(p ** k * (q ** n1 - eps) // gcd(d, n1)) k += 1 # (4) a4 = MixedElements(q, n, lambda k: p ** (k - 1) + 1, lambda k: p ** k, min_length=2, sign=e) # (5) k = numeric.get_exponent(n - 1, p) a5 = [] if k is None else [p * (n - 1) * d] # (6) a6 = [p * gcd(2, q - 1) * (q + e)] if n == 4 else [] return itertools.chain(a1, a2, a3, a4, a5, a6)
def spectrum(n, field): q = field.order p = field.char d = gcd(n, q - e) # (1) eps = 1 if n % 2 == 0 else e a1 = [(q ** n - eps) // ((q - e) * d)] # (2) a2 = [] eps = lambda s: 1 if s % 2 == 0 else e for n1 in xrange(1, (n + 2) // 2): pair = (n1, n - n1) signs = (-eps(n1), -eps(n - n1)) a2.append(lcm(q ** pair[0] + signs[0], q ** pair[1] + signs[1]) // gcd(n // gcd(n1, n - n1), q - e)) # (3) a3 = SemisimpleElements(q, n, min_length=3, sign=e) # (4) a4 = [] k = 1 while True: n1 = n - p ** (k - 1) - 1 if n1 < 1: break eps = 1 if n1 % 2 == 0 else e a4.append(p ** k * (q ** n1 - eps) / d) k += 1 # (5) a5 = MixedElements(q, n, lambda k: p ** (k - 1) + 1, lambda k: p ** k, min_length=2, sign=e) # (6) k = numeric.get_exponent(n - 1, p) a6 = [] if k is None else [p * (n - 1)] return itertools.chain(a1, a2, a3, a4, a5, a6)
def _omega_pm_spectrum_odd_c(n, field, sign): """Spectra of Omega^e_{2n}(q) for odd q. [1, Corollary 8] """ n //= 2 q = field.order p = field.char nk = lambda k: (p**(k - 1) + 3) // 2 # (1) a1 = [(q**n - sign) // 2] # (2) a2 = SemisimpleElements(q, n, min_length=2, parity=sign) # (3) a3 = [] k = 1 while True: n_k = nk(k) if n_k >= n: break dk = gcd(4, q**n_k - sign) // 2 a3.append(p**k * lcm(dk, (q**(n - n_k) + 1) // dk)) a3.append(p**k * lcm(dk, (q**(n - n_k) - 1) // dk)) k += 1 # (4) a4 = MixedElements(q, n, nk, lambda k: p**k, min_length=2) # (5) a5 = [] for elem in SemisimpleElements(q, n - 2, min_length=2, parity=sign): a5.append(elem.lcm(SpectraElement(p, q, [1], [-1]))) a5.append(elem.lcm(SpectraElement(p, q, [1], [1]))) # (6) t = (q**(n - 2) - sign) // 2 a6 = [p * lcm(q - 1, t), p * lcm(q + 1, t)] # (7) k = numeric.get_exponent(2 * n - 3, p) a7 = [] if k is None else [p * (2 * n - 3) * gcd(4, q**n - sign) // 2] # (8) a8 = [p * (q * q - 1), p * (q * q + 1)] if n == 4 and sign == 1 else [] # (9) a9 = [9 * (q - 1), 9 * (q + 1)] if n == 4 and p == 3 and sign == 1 else [] return itertools.chain(a1, a2, a3, a4, a5, a6, a7, a8, a9)
def _add_element(self, a): """Add new spectrum element """ # these are the indices of future neighbors of a neighbors = [] # memorize initial length so that we don't have to process newly added # vertices l = len(self._vertices) for i in range(l): b = self._vertices[i] d = numeric.gcd(a, b) if d == 1: continue bd = numeric.prime_part(b, d) if bd == 1: self._vertices[i] = d for neighbor in neighbors: self._set_adjacency(i, neighbor, True) neighbors.append(i) else: self._vertices[i] = bd dIndex = self.clone_vertex(i, d) for neighbor in neighbors: self._adjacency[dIndex][neighbor] = True neighbors.append(dIndex) a = numeric.prime_part(a, d) if a == 1: break if a > 1: index = self._add_vertex(a) for neighbor in neighbors: self._set_adjacency(index, neighbor, True)
def _add_element(self, a): """Add new spectrum element """ # these are the indices of future neighbors of a neighbors = [] # memorize initial length so that we don't have to process newly added # vertices l = len(self._vertices) for i in range(l): b = self._vertices[i] d = numeric.gcd(a, b) if d == 1: continue bd = numeric.prime_part(b, d) if bd == 1: self._vertices[i] = d for neighbor in neighbors: self._set_adjacency(i, neighbor, True) neighbors.append(i) else: self._vertices[i] = bd dIndex = self.clone_vertex(i, d) for neighbor in neighbors: self._adjacency[dIndex][neighbor] = True neighbors.append(dIndex) a = numeric.prime_part(a, d) if a == 1: break if a > 1: index = self._add_vertex(a) for neighbor in neighbors: self._set_adjacency(index, neighbor, True)
def _projective_special_unitary_order(n, field): q = field.order return (Integer({field.char: field.pow * (n * (n - 1) / 2)}) * prod( (Integer(q**i - 1) * Integer(q**i + 1) for i in xrange(2, n // 2 + 1))) * prod( (Integer(q**(2 * i + 1) + 1)) for i in xrange(1, (n + 1) // 2)) * Integer(q - 1) * Integer( (q + 1) // gcd(n, q + 1)))
def _projective_special_unitary_order(n, field): q = field.order return (Integer({field.char: field.pow * (n * (n - 1) / 2)}) * prod((Integer(q ** i - 1) * Integer(q ** i + 1) for i in xrange(2, n // 2 + 1))) * prod((Integer(q ** (2 * i + 1) + 1)) for i in xrange(1, (n + 1) // 2)) * Integer(q - 1) * Integer((q + 1) // gcd(n, q + 1)))
def spectrum(n, field): q = field.order p = field.char d = gcd(n, q - e) # (1) eps = 1 if n % 2 == 0 else e a1 = [(q**n - eps) // ((q - e) * d)] # (2) a2 = [] eps = lambda s: 1 if s % 2 == 0 else e for n1 in xrange(1, (n + 2) // 2): pair = (n1, n - n1) signs = (-eps(n1), -eps(n - n1)) a2.append( lcm(q**pair[0] + signs[0], q**pair[1] + signs[1]) // gcd(n // gcd(n1, n - n1), q - e)) # (3) a3 = SemisimpleElements(q, n, min_length=3, sign=e) # (4) a4 = [] k = 1 while True: n1 = n - p**(k - 1) - 1 if n1 < 1: break eps = 1 if n1 % 2 == 0 else e a4.append(p**k * (q**n1 - eps) / d) k += 1 # (5) a5 = MixedElements(q, n, lambda k: p**(k - 1) + 1, lambda k: p**k, min_length=2, sign=e) # (6) k = numeric.get_exponent(n - 1, p) a6 = [] if k is None else [p * (n - 1)] return itertools.chain(a1, a2, a3, a4, a5, a6)
def order(n, field): omega_order = _omega_pm_order(e)(n, field) q = field.order n //= 2 # gcd(4, q^n-e) omega_order.div_by_prime(2) if e == 1: divisor = 1 if (n % 2 == 1 and q % 4 == 3) else 2 else: divisor = 2 if (n % 2 == 1 and q % 4 == 3) else 1 if divisor > 1: omega_order.div_by_prime(2) return omega_order * gcd(q - e, 2)
def order(n, field): omega_order = _omega_pm_order(e)(n, field) q = field.order n //= 2 # gcd(4, q^n-e) omega_order.div_by_prime(2) if e == 1: divisor = 1 if (n % 2 == 1 and q % 4 == 3) else 2 else: divisor = 2 if (n % 2 == 1 and q % 4 == 3) else 1 if divisor > 1: omega_order.div_by_prime(2) return omega_order * gcd(q - e, 2)
def _omega_pm_spectrum_odd_c(n, field, sign): n //= 2 q = field.order p = field.char nk = lambda k: (p ** (k - 1) + 3) // 2 # (1) a1 = [(q ** n - sign) // 2] # (2) a2 = SemisimpleElements(q, n, min_length=2, parity=sign) # (3) a3 = [] k = 1 while True: n_k = nk(k) if n_k >= n: break dk = gcd(4, q ** n_k - sign) // 2 a3.append(p ** k * lcm(dk, (q ** (n - n_k) + 1) // dk)) a3.append(p ** k * lcm(dk, (q ** (n - n_k) - 1) // dk)) k += 1 # (4) a4 = MixedElements(q, n, nk, lambda k: p ** k, min_length=2) # (5) a5 = [] for elem in SemisimpleElements(q, n - 2, min_length=2, parity=sign): a5.append(elem.lcm(SpectraElement(p, q, [1], [-1]))) a5.append(elem.lcm(SpectraElement(p, q, [1], [1]))) # (6) t = (q ** (n - 2) - sign) // 2 a6 = [p * lcm(q - 1, t), p * lcm(q + 1, t)] # (7) k = numeric.get_exponent(2 * n - 3, p) a7 = [] if k is None else [p * (2 * n - 3) * gcd(4, q ** n - sign) // 2] # (8) a8 = [p * (q * q - 1), p * (q * q + 1)] if n == 4 and sign == 1 else [] # (9) a9 = [9 * (q - 1), 9 * (q + 1)] if n == 4 and p == 3 and sign == 1 else [] return itertools.chain(a1, a2, a3, a4, a5, a6, a7, a8, a9)
def spectrum(field): q = field.order p = field.char d = gcd(3, q - e) # (1) a1 = [(q**6 - 1) // d, (q**6 + e * q**3 + 1) // d, (q * q + e * q + 1) * (q**4 - q * q + 1) // d, (q - e) * (q * q + 1) * (q**3 + e) // d, (q * q - 1) * (q**4 + 1) // d, (q + e) * (q**5 - e) // d, q**5 - e] # (2) a2 = [ p * x for x in [(q**6 - 1) // (d * (q - e)), (q**5 - e) // d, q**4 - 1, (q**3 - e) * (q + e), (q - e) * (q**3 + e) // d] ] # (3) pA2 = 4 if p == 2 else p a3 = [ pA2 * x for x in [(q**3 - e) * (q + e) // d, (q**4 + q * q + 1) // d, (q**4 - 1) // d] ] # (4) pA3 = p * p if p in (2, 3) else p a4 = [pA3 * x for x in [(q * q + 1) * (q - e) // d, q**q - 1]] # (5) pD4 = 8 if p == 2 else p * p if p in (3, 5) else p a5 = [ pD4 * x for x in [q - e, (q * q - 1) // d, (q * q + e * q + 1) // d] ] # (6) pD5 = 8 if p == 2 else p * p if p in (3, 5, 7) else p a6 = [pD5 * (q - e) // d] # (7) pE6 = 16 if p == 2 else 27 if p == 3 else p * p if p in (5, 7, 11) else p a7 = [pE6] return itertools.chain(a1, a2, a3, a4, a5, a6, a7)
def _e6_order(field): q = field.order return (_order_product(field, 36, [6, 4, 3, 3, 2, 1, 1], [9, 5, 3, 3, 1]) * Integer((q - 1) // gcd(3, q - 1)))
def test_symplectic_gcd(self, n): max_elems = max_orders.symplectic_2(n) expected = numeric.gcd(*max_elems) self.assertEqual(expected, max_orders.symplectic_2_gcd(n))
def _projective_special_linear_order(n, field): q = field.order return (Integer({field.char: field.pow * (n * (n - 1) / 2)}) * prod((Integer(q ** i - 1) for i in xrange(3, n + 1))) * Integer(q + 1) * Integer((q - 1) // gcd(n, q - 1)))
def _e6_order(field): q = field.order return (_order_product(field, 36, [6, 4, 3, 3, 2, 1, 1], [9, 5, 3, 3, 1]) * Integer((q - 1) // gcd(3, q - 1)))
def _e7_order(field): q = field.order return (_order_product(field, 63, [9, 7, 6, 5, 4, 3, 3, 2, 1, 1], [9, 7, 5, 3, 3, 1]) * Integer((q - 1) // gcd(2, q - 1)))
def _2e6_order(field): q = field.order return (_order_product(field, 36, [9, 6, 5, 4, 3, 3, 2, 1], [3, 3, 1, 1]) * Integer((q + 1) // gcd(3, q + 1)))
def _projective_special_linear_order(n, field): q = field.order return (Integer({field.char: field.pow * (n * (n - 1) / 2)}) * prod( (Integer(q**i - 1) for i in xrange(3, n + 1))) * Integer(q + 1) * Integer( (q - 1) // gcd(n, q - 1)))
def _e7_order(field): q = field.order return (_order_product(field, 63, [9, 7, 6, 5, 4, 3, 3, 2, 1, 1], [9, 7, 5, 3, 3, 1]) * Integer( (q - 1) // gcd(2, q - 1)))
def _2e6_order(field): q = field.order return (_order_product(field, 36, [9, 6, 5, 4, 3, 3, 2, 1], [3, 3, 1, 1]) * Integer((q + 1) // gcd(3, q + 1)))