def analyze_deeply(tri, angle): N = edge_equation_matrix_taut(tri, angle) N = Matrix(N) M = snappy.Manifold(tri.snappystring()) # look at it alex = alex_is_monic(M) hyper = hyper_is_monic(M) non_triv, non_triv_sol = non_trivial_solution(N) full, full_sol = fully_carried_solution(N) try: assert non_triv or not full # full => non_triv assert alex or not full # full => fibered => alex is monic assert hyper or not full # full => fibered => hyper is monic assert alex or not hyper # hyper is monic => alex is monic except AssertError: print("contradiction in maths") raise if full: pass elif non_triv: print("non-triv sol (but not full)") print((alex, hyper)) elif not alex or not hyper: print("no sol") print((alex, hyper)) return None
def get_non_triv_sol(tri, angle): N = edge_equation_matrix_taut(tri, angle) N = Matrix(N) non_triv, sol = non_trivial_solution(N, real_bool = False, int_bool = True) twiddles = is_transverse_taut(tri, angle, return_type = "face_coorientations") sol = [int(a * b) for a, b in zip(sol, twiddles)] return sol
def is_layered(tri, angle): """ Given a tri, angle decide if it is layered. """ N = edge_equation_matrix_taut(tri, angle) N = Matrix(N) layered, _ = fully_carried_solution(N) return layered
def min_carried_neg_euler(tri, angle): """ Given a tri, angle, find the minimal negative euler characteristic among carried surfaces. Returns zero if there is none such. """ N = edge_equation_matrix_taut(tri, angle) N = Matrix(N) _, sol = non_trivial_solution(N, real_bool = False, int_bool = True) if sol == None: out = 0.0 else: out = sum(sol)/2 # sum counts triangles, so divide return out
def taut_rays(tri, angle): # get the extreme rays of the taut cone - note that the returned # vectors are non-negative because they "point up" N = edge_equation_matrix_taut(tri, angle) N = Matrix(N) dim = N.dimensions()[1] elem_ieqs = [[0] + list(elem_vector(i, dim)) for i in range(dim)] N_rows = [v.list() for v in N.rows()] N_eqns = [[0] + v for v in N_rows] P = Polyhedron(ieqs = elem_ieqs, eqns = N_eqns) rays = [ray.vector() for ray in P.rays()] for ray in rays: assert all(a.is_integer() for a in ray) # all of the entries are integers, represented in QQ, so we clean them. return [vector(ZZ(a) for a in ray) for ray in rays]
def LMN_tri_angle(tri, angle): """ Given a tri, angle, decide LMN """ N = edge_equation_matrix_taut(tri, angle) N = Matrix(N) farkas, farkas_sol = farkas_solution(N) non_triv, non_triv_sol = non_trivial_solution(N) full, full_sol = fully_carried_solution(N) if full: out = "L" elif non_triv: out = "M" else: assert farkas out = "N" return out
def carries_torus_or_sphere(tri, angle): """ Given a tri, angle decides if there is a once-punctured torus or three-times punctured sphere among the carried surfaces. """ N = edge_equation_matrix_taut(tri, angle) # We must decide if there is a pair of columns which are negatives # of each other. We could test on quadratically many vectors, or # we could do this: N = Matrix(N).transpose() # easier to work with rows N = set(tuple(row) for row in N) # make rows unique N = Matrix(N) P = [] for row in N: P.append(row) P.append(-row) P.sort() for i in range(len(P) - 1): if P[i] == P[i+1]: return True return False