Cluster Pictures¶
- class sage_cluster_pictures.cluster_pictures.BYTree(*args, **kwargs)¶
Bases:
Graph
Construct a BY tree.
EXAMPLES:
- __init__(*args, **kwargs)¶
See
BYTree
for documentation.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T BY tree with 0 yellow vertices, 0 blue vertices, 0 yellow edges, 0 blue edges
TESTS:
sage: #C = BYTree() sage: #TestSuite(C).run()
- _repr_()¶
Return a string representation of
self
.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T.add_blue_vertex('v1', 1) sage: T.add_blue_vertex('v2', 2) sage: T.add_yellow_vertex('v3') sage: T.add_yellow_vertex('v4') sage: T.add_yellow_edge(('v4', 'v1', 1)) sage: T.add_yellow_edge(('v4', 'v2', 1)) sage: T.add_blue_edge(('v3', 'v4', 2)) sage: T BY tree with 2 yellow vertices, 2 blue vertices, 2 yellow edges, 1 blue edges
- add_blue_edge(a)¶
Adds a blue edge to the BY tree.
INPUT:
a
- triple of vertices and a weight.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T.add_blue_vertex('v1', 1) sage: T.add_blue_vertex('v2', 2) sage: T.add_yellow_vertex('v3') sage: T.add_yellow_vertex('v4') sage: T.add_yellow_edge(('v4', 'v1', 1)) sage: T.add_yellow_edge(('v4', 'v2', 1)) sage: T.add_blue_edge(('v3', 'v4', 2)) sage: T BY tree with 2 yellow vertices, 2 blue vertices, 2 yellow edges, 1 blue edges
- add_blue_edges(B)¶
Adds a sequence of blue edges
B
toself
.INPUT:
B
- an iterable containing valid inputs foradd_blue_edge()
.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T.add_blue_vertices(['b1', 'b2', 'b3', 'b4', 'b5', 'b6', 'b7']) sage: T.add_yellow_vertex('Y') sage: T.add_blue_edges([('b1', 'Y', 2), ('b2', 'Y', 2), ('b5', 'Y', 1), ('b6', 'Y', 4), ('b3', 'b4', 1), ('b7', 'b4', 1)]) sage: T BY tree with 1 yellow vertices, 7 blue vertices, 0 yellow edges, 6 blue edges
- add_blue_vertex(label, genus=0)¶
Adds a blue vertex to the BY tree.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T.add_blue_vertex('v1', 0) sage: T BY tree with 0 yellow vertices, 1 blue vertices, 0 yellow edges, 0 blue edges sage: T.add_blue_vertex('v2', 1) sage: T BY tree with 0 yellow vertices, 2 blue vertices, 0 yellow edges, 0 blue edges sage: T.add_blue_vertex('v3') sage: T.genus('v3') 0
- add_blue_vertices(labels, genera=None)¶
Adds a sequence of blue vertices given by
labels
toself
, optionally with genera.INPUT:
labels
- an iterable containing valid inputs foradd_blue_vertex()
.genera
(optional) - an iterable containing the same number of inputs aslabels
, specifying a genus for each vertex.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T.add_blue_vertices(['b1', 'b2', 'b3', 'b4', 'b5', 'b6', 'b7']) sage: T.add_yellow_vertex('Y') sage: T.add_blue_edges([('b1', 'Y', 2), ('b2', 'Y', 2), ('b5', 'Y', 1), ('b6', 'Y', 4), ('b3', 'b4', 1), ('b7', 'b4', 1)]) sage: T BY tree with 1 yellow vertices, 7 blue vertices, 0 yellow edges, 6 blue edges sage: T.add_blue_vertices(['b8', 'b9'], [1, 2]) sage: T BY tree with 1 yellow vertices, 9 blue vertices, 0 yellow edges, 6 blue edges
- add_yellow_edge(a)¶
Adds a yellow edge to the BY tree.
INPUT:
a
- triple of vertices and a weight.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T.add_blue_vertex('v1', 1) sage: T.add_blue_vertex('v2', 2) sage: T.add_yellow_vertex('v3') sage: T.add_yellow_vertex('v4') sage: T.add_yellow_edge(('v4', 'v1', 1)) sage: T.add_yellow_edge(('v4', 'v2', 1)) sage: T.add_blue_edge(('v3', 'v4', 2)) sage: T BY tree with 2 yellow vertices, 2 blue vertices, 2 yellow edges, 1 blue edges
- add_yellow_edges(Y)¶
Adds a sequence of yellow edges
Y
toself
.INPUT:
Y
- an iterable containing valid inputs foradd_yellow_edge()
.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree(name="Stick person") sage: T.add_blue_vertices(['b1', 'b2', 'b3', 'b4', 'b5', 'b6', 'b7']) sage: T.add_yellow_vertex('Y') sage: T.add_yellow_edges([('b1', 'Y', 2), ('b2', 'Y', 2), ('b5', 'Y', 1), ('b6', 'Y', 4), ('b3', 'b4', 1), ('b7', 'b4', 1)]) sage: T.add_blue_edge(('b6', 'b4', 1)) sage: T BY tree with 1 yellow vertices, 7 blue vertices, 6 yellow edges, 1 blue edges
- add_yellow_vertex(label)¶
Adds a yellow vertex to the BY tree.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T.add_yellow_vertex('v1') sage: T BY tree with 1 yellow vertices, 0 blue vertices, 0 yellow edges, 0 blue edges sage: T.add_yellow_vertex('v2') sage: T BY tree with 2 yellow vertices, 0 blue vertices, 0 yellow edges, 0 blue edges
- add_yellow_vertices(labels)¶
Adds a sequence of yellow vertices given by
labels
toself
.INPUT:
labels
- an iterable containing valid inputs foradd_yellow_vertex()
.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T.add_yellow_vertices(['b1', 'b2', 'b3', 'b4', 'b5', 'b6', 'b7']) sage: T.add_yellow_vertex('Y') sage: T BY tree with 8 yellow vertices, 0 blue vertices, 0 yellow edges, 0 blue edges
- blue_edges()¶
Return the list of yellow vertices of
self
.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T.add_blue_vertex('v1', 1) sage: T.add_blue_vertex('v2', 2) sage: T.add_yellow_vertex('v3') sage: T.add_yellow_vertex('v4') sage: T.add_yellow_edge(('v4', 'v1', 1)) sage: T.add_yellow_edge(('v4', 'v2', 1)) sage: T.add_blue_edge(('v3', 'v4', 2)) sage: T.blue_edges() [('v3', 'v4', 2)]
- blue_subgraph()¶
Return the blue subgraph of
self
.This is the subgraph consisting of blue edges and vertices. Note that by assumption no blue edge is incident to a yellow vertex.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T.add_blue_vertex('v1', 1) sage: T.add_blue_vertex('v2', 0) sage: T.add_yellow_edge(('v1', 'v2', 2)) sage: T.blue_subgraph() BY tree with 0 yellow vertices, 2 blue vertices, 0 yellow edges, 0 blue edges
- blue_vertices()¶
Return the list of blue vertices of
self
.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T.add_blue_vertex('v1', 0) sage: T.add_blue_vertex('v2', 1) sage: T.add_yellow_vertex('v3') sage: T.blue_vertices() ['v1', 'v2']
- centre()¶
Gives the centre of a BY tree as a list of one or two vertices. This also outputs the W function on the vertices.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: x = polygen(Qp(7,150)) sage: f = (x^3 - 7^15)*(x^2-7^6)*(x^3-7^3) sage: BYT = Cluster.from_polynomial(f).BY_tree() sage: BYT.centre() ([Cluster with 5 roots and 3 children], {Cluster with 3 roots and 3 children: 3, Cluster with 5 roots and 3 children: 8, Cluster with 8 roots and 4 children: 3}) sage: f = 7*(x^2+1)*(x^2+36)*(x^2+64) sage: BYT = Cluster.from_polynomial(f).BY_tree() sage: BYT.centre() ([Cluster with 3 roots and 3 children, Cluster with 3 roots and 3 children], {Cluster with 3 roots and 3 children: 3, Cluster with 3 roots and 3 children: 3})
- contract_odd_order_subtree(F)¶
Returns a BY tree obtained from
self
by contracting the subtree on whichF
acts with odd order into a blue vertex, along with the inducedBYTreeIsomorphism
ofF
on the new tree. Note that this mutates the original graph.
- degree_ge_three_vertices()¶
Return all degree \ge 3 vertices of
self
.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster, BYTree sage: x = polygen(Qp(7,150)) sage: H = HyperellipticCurve((x^2 + 7^2)*(x^2 - 7^15)*(x - 7^6)*(x - 7^6 - 7^9)) sage: T = Cluster.from_curve(H).BY_tree() sage: T.degree_ge_three_vertices() [Cluster with 4 roots and 2 children] sage: K = Qp(5) sage: x = polygen(K) sage: R = Cluster.from_polynomial((x^4-5^4)*(x+1)*(x+2)) sage: T = R.BY_tree() sage: T.degree_ge_three_vertices() [] sage: T = BYTree() sage: T.add_blue_vertex(1) sage: T.add_blue_vertex(2) sage: T.add_blue_vertex(3) sage: T.add_blue_vertex(4) sage: T.add_yellow_vertex(5) sage: T.add_yellow_edge((1, 5, 1)) sage: T.add_yellow_edge((2, 5, 1)) sage: T.add_yellow_edge((3, 5, 1)) sage: T.add_yellow_edge((4, 5, 1)) sage: T.degree_ge_three_vertices() [5]
- delete_vertex(label)¶
Deletes a vertex and all incident edges from the BY tree.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T.add_yellow_vertex('v1') sage: T.add_yellow_vertex('v2') sage: T.add_blue_edge(('v1','v2',2)) sage: T.delete_vertex('v1') sage: T BY tree with 1 yellow vertices, 0 blue vertices, 0 yellow edges, 0 blue edges sage: T = BYTree() sage: T.add_yellow_vertex('v1') sage: T.add_yellow_vertex('v2') sage: T.add_blue_edge(('v2','v1',2)) sage: T.delete_vertex('v1') sage: T BY tree with 1 yellow vertices, 0 blue vertices, 0 yellow edges, 0 blue edges sage: T = BYTree() sage: T.add_yellow_vertex('v1') sage: T.add_yellow_vertex('v2') sage: T.add_yellow_edge(('v1','v2',2)) sage: T.delete_vertex('v1') sage: T BY tree with 1 yellow vertices, 0 blue vertices, 0 yellow edges, 0 blue edges sage: T = BYTree() sage: T.add_yellow_vertex('v1') sage: T.add_yellow_vertex('v2') sage: T.add_yellow_edge(('v2','v1',2)) sage: T.delete_vertex('v1') sage: T BY tree with 1 yellow vertices, 0 blue vertices, 0 yellow edges, 0 blue edges
- genus(vertex)¶
Return the genus of a vertex.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T.add_blue_vertex('v1', 0) sage: T.genus('v1') 0 sage: T.add_blue_vertex('v2', 1) sage: T.genus('v2') 1 sage: T.add_yellow_vertex('v3') sage: T.genus('v3') 0
- graphplot(**options)¶
- is_blue(e)¶
Check if an edge e of
self
is blue.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T.add_blue_vertex('v1', 1) sage: T.add_blue_vertex('v2', 2) sage: T.add_blue_vertex('v3', 2) sage: T.add_yellow_edge(('v2', 'v1', 1)) sage: T.is_blue(T.edges(sort=False)[0]) False sage: T.add_blue_edge(('v3', 'v1', 1)) sage: T.is_blue(T.edges_incident('v3')[0]) True
- is_yellow(e)¶
Check if an edge e of
self
is yellow.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T.add_blue_vertex('v1', 1) sage: T.add_blue_vertex('v2', 2) sage: T.add_blue_vertex('v3', 2) sage: T.add_yellow_edge(('v2', 'v1', 1)) sage: T.is_yellow(T.edges(sort=False)[0]) True sage: T.add_blue_edge(('v3', 'v1', 1)) sage: T.is_yellow(T.edges_incident('v3')[0]) False
- minimal_discriminant(frob=None)¶
Computes the valuation of the minimal discriminant of the BY tree. In some cases, it is required to give the Frobenius automorphism.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: x = polygen(Qp(7,150)) sage: f = (x^3 - 7^15)*(x^2-7^6)*(x^3-7^3) sage: BYT = Cluster.from_polynomial(f).BY_tree() sage: BYT.minimal_discriminant() 24
Example 15.7:
sage: f = 7*(x^2+1)*(x^2+36)*(x^2+64) sage: BYT, F = Cluster.from_polynomial(f).BY_tree(with_frob = True) sage: BYT.minimal_discriminant(frob=F) 22
Example 15.6:
sage: p = 11 sage: x = polygen(Qp(p, 200)) sage: C = Cluster.from_polynomial(p*(x^2-p^5)*(x^3-p^3)*((x-1)^3-p^9)) sage: T,F = C.BY_tree(with_frob=True) sage: T.minimal_discriminant(frob=F) 27
- multiway_cuts(vertices)¶
Return all unordered n-tuples of edges of
self
such that their removal disconnects the n + 1vertices
provided.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: G = BYTree() sage: G.add_yellow_vertex(1) sage: G.add_yellow_vertex(2) sage: G.add_yellow_edge((1,2,1)) sage: list(G.multiway_cuts([1,2])) [[(1, 2, 1)]] sage: G.add_yellow_vertex(3) sage: G.add_yellow_edge((2,3,1)) sage: list(G.multiway_cuts([1,2,3])) [[(1, 2, 1), (2, 3, 1)]] sage: list(G.multiway_cuts([1,3])) [[(1, 2, 1)], [(2, 3, 1)]] sage: G.add_yellow_edge((1,3,1)) sage: list(G.multiway_cuts([1,3])) [] sage: list(G.multiway_cuts([1,2,3])) [] sage: list(G.multiway_cuts([1,2,3])) [] sage: G.add_yellow_vertex(4) sage: G.add_yellow_edge((2,4,1)) sage: list(G.multiway_cuts([1,2,3])) [] sage: list(G.multiway_cuts([1,2,4])) []
- quotient(F)¶
Quotient
self
by the automorphismF
.EXAMPLES:
Example 4.11:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qq(11^3, 200, names="a") sage: a = K.gen() sage: z = K.teichmuller(10*a^2 + 7*a + 8) sage: x = polygen(K) sage: f = prod(x-a for a in [0,1,2,z-11,z+11,z^2 - 11, z^2 +11, z^4 -11, z^4 + 11]).map_coefficients(lambda x: x.trace()/3, new_base_ring=Qp(11, 200)) sage: R = Cluster.from_polynomial(f) sage: T, F = R.BY_tree(with_frob=True) sage: T.quotient(F) BY tree with 0 yellow vertices, 2 blue vertices, 1 yellow edges, 0 blue edges sage: x = polygen(Qp(7,150)) sage: H = HyperellipticCurve((x^2 + 7^2)*(x^2 - 7^15)*(x - 7^6)*(x - 7^6 - 7^9)) sage: R = Cluster.from_curve(H) sage: T, F = R.BY_tree(with_frob=True) sage: T.quotient(F) BY tree with 1 yellow vertices, 3 blue vertices, 3 yellow edges, 0 blue edges
- sign_vertex(component)¶
Return the vertex of
self
used to compute the sign of the yellow componentcomponent
in an automorphism.This is any vertex in the closure of
component
, which is either yellow or not the parent of a cluster \mathfrak t with v_{\mathfrak t} also in this closure.NOTE:
This depends on parent child relationships of vertices, so does not work for arbitrary BY trees, only those coming from clusters.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster, BYTree sage: x = polygen(Qp(7,150)) sage: H = HyperellipticCurve((x^2 + 7^2)*(x^2 - 7^15)*(x - 7^6)*(x - 7^6 - 7^9)) sage: R = Cluster.from_curve(H) sage: T = R.BY_tree() sage: T.sign_vertex([T.yellow_edges()[0]]) Cluster with 4 roots and 2 children
- subgraph(*args, **options)¶
Return the subgraph containing the given vertices and edges.
If either vertices or edges are not specified, they are assumed to be all vertices or edges. If edges are not specified, returns the subgraph induced by the vertices.
INPUT:
inplace
– boolean (default:False
); usinginplace=True
will simply delete the extra vertices and edges from the current graph. This will modify the graph.vertices
– a single vertex or an iterable container of vertices, e.g. a list, set, graph, file or numeric array. If not passed (i.e.,None
), defaults to the entire graph.edges
– as withvertices
, edges can be a single edge or an iterable container of edges (e.g., a list, set, file, numeric array, etc.). By default (edges=None
), all edges are assumed and the returned graph is an induced subgraph. In the case of multiple edges, specifying an edge as (u,v) means to keep all edges (u,v), regardless of the label.vertex_property
– function (default:None
); a function that inputs a vertex and outputs a boolean value, i.e., a vertexv
invertices
is kept ifvertex_property(v) == True
edge_property
– function (default:None
); a function that inputs an edge and outputs a boolean value, i.e., a edgee
inedges
is kept ifedge_property(e) == True
algorithm
– string (default:None
); one of the following:If
algorithm="delete"
orinplace=True
, then the graph is constructed by deleting edges and verticesIf
algorithm="add"
, then the graph is constructed by building a new graph from the appropriate vertices and edges. Impliesinplace=False
.If
algorithm=None
, then the algorithm is chosen based on the number of vertices in the subgraph.
immutable
– boolean (default:None
); whether to create a mutable/immutable subgraph.immutable=None
(default) means that the graph and its subgraph will behave the same way.
EXAMPLES:
sage: G = graphs.CompleteGraph(9) sage: H = G.subgraph([0, 1, 2]); H Subgraph of (Complete graph): Graph on 3 vertices sage: G Complete graph: Graph on 9 vertices sage: J = G.subgraph(edges=[(0, 1)]) sage: J.edges(sort=True, labels=False) [(0, 1)] sage: set(J) == set(G) True sage: G.subgraph([0, 1, 2], inplace=True); G Subgraph of (Complete graph): Graph on 3 vertices sage: G.subgraph() == G True
sage: D = digraphs.Complete(9) sage: H = D.subgraph([0, 1, 2]); H Subgraph of (Complete digraph): Digraph on 3 vertices sage: H = D.subgraph(edges=[(0, 1), (0, 2)]) sage: H.edges(sort=True, labels=False) [(0, 1), (0, 2)] sage: set(H) == set(D) True sage: D Complete digraph: Digraph on 9 vertices sage: D.subgraph([0, 1, 2], inplace=True); D Subgraph of (Complete digraph): Digraph on 3 vertices sage: D.subgraph() == D True
A more complicated example involving multiple edges and labels:
sage: G = Graph(multiedges=True, sparse=True) sage: G.add_edges([(0, 1, 'a'), (0, 1, 'b'), (1, 0, 'c'), (0, 2, 'd'), (0, 2, 'e'), (2, 0, 'f'), (1, 2, 'g')]) sage: G.subgraph(edges=[(0, 1), (0, 2,'d'), (0, 2, 'not in graph')]).edges(sort=True) [(0, 1, 'a'), (0, 1, 'b'), (0, 1, 'c'), (0, 2, 'd')] sage: J = G.subgraph(vertices=[0, 1], edges=[(0, 1, 'a'), (0, 2, 'c')]) sage: J.edges(sort=True) [(0, 1, 'a')] sage: J.vertices(sort=True) [0, 1] sage: G.subgraph(vertices=G) == G True
sage: D = DiGraph(multiedges=True, sparse=True) sage: D.add_edges([(0, 1, 'a'), (0, 1, 'b'), (1, 0, 'c'), (0, 2, 'd'), (0, 2, 'e'), (2, 0, 'f'), (1, 2, 'g')]) sage: D.subgraph(edges=[(0, 1), (0, 2, 'd'), (0, 2, 'not in graph')]).edges(sort=True) [(0, 1, 'a'), (0, 1, 'b'), (0, 2, 'd')] sage: H = D.subgraph(vertices=[0, 1], edges=[(0, 1, 'a'), (0, 2, 'c')]) sage: H.edges(sort=True) [(0, 1, 'a')] sage: H.vertices(sort=True) [0, 1]
Using the property arguments:
sage: P = graphs.PetersenGraph() sage: S = P.subgraph(vertex_property=lambda v: not (v % 2)) sage: S.vertices(sort=True) [0, 2, 4, 6, 8]
sage: C = graphs.CubeGraph(2) sage: S = C.subgraph(edge_property=(lambda e: e[0][0] == e[1][0])) sage: C.edges(sort=True) [('00', '01', None), ('00', '10', None), ('01', '11', None), ('10', '11', None)] sage: S.edges(sort=True) [('00', '01', None), ('10', '11', None)]
The algorithm is not specified, then a reasonable choice is made for speed:
sage: g = graphs.PathGraph(1000) sage: g.subgraph(list(range(10))) # uses the 'add' algorithm Subgraph of (Path graph): Graph on 10 vertices
TESTS:
The appropriate properties are preserved:
sage: g = graphs.PathGraph(10) sage: g.is_planar(set_embedding=True) True sage: g.set_vertices({v: 'v%d'%v for v in g}) sage: h = g.subgraph([3..5]) sage: sorted(h.get_pos().keys()) [3, 4, 5] sage: h.get_vertices() {3: 'v3', 4: 'v4', 5: 'v5'}
- tamagawa_number(F)¶
Compute the Tamagawa number of
self
with respect to the automorphismF
.INPUT:
F
- ABYTreeIsomorphism
fromself
toself
.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree, Cluster, BYTreeIsomorphism sage: K = Qp(5,150) sage: x = polygen(K) sage: R = Cluster.from_polynomial((x^4-5^4)*(x+1)*(x+2)) sage: T, F = R.BY_tree(with_frob=True) sage: T.tamagawa_number(F) 2
We can use symbols even as in Betts 3.3.1:
sage: a, b, c = var('a b c', domain="positive") sage: R = Cluster([[oo, a/2, 0, 0, 0, 0, 0, 0], ....: [a/2, oo, 0, 0, 0, 0, 0, 0], ....: [0, 0, oo, b/2, 0, 0, 0, 0], ....: [0, 0, b/2, oo, 0, 0, 0, 0], ....: [0, 0, 0, 0, oo, c/2, 0, 0], ....: [0, 0, 0, 0, c/2, oo, 0, 0], ....: [0, 0, 0, 0, 0, 0, oo, c/2], ....: [0, 0, 0, 0, 0, 0, c/2, oo], ]) sage: R Cluster with 8 roots and 4 children sage: C1,C2 = [r for r in R.children() if r.depth() == c/2] sage: A = [r for r in R.children() if r.depth() == a/2][0] sage: B = [r for r in R.children() if r.depth() == b/2][0] sage: T = R.BY_tree() sage: T BY tree with 1 yellow vertices, 4 blue vertices, 4 yellow edges, 0 blue edges sage: F = BYTreeIsomorphism(T, T, ....: lambda x: {A:A, B:B, C1:C2, C2:C1, R:R}[x], ....: lambda Y: 1) sage: T.tamagawa_number(F) 2*a*b + a*c + b*c sage: F = BYTreeIsomorphism(T, T, ....: lambda x: {A:A, B:B, C1:C2, C2:C1, R:R}[x], ....: lambda Y: -1) sage: #T.tamagawa_number(F) if only TODO
Example 10.5:
sage: a, b, c = var('a b c', domain="positive") sage: R = Cluster([[oo, a/2, 0, 0, 0, 0, ], ....: [a/2, oo, 0, 0, 0, 0, ], ....: [0, 0, oo, b/2, 0, 0, ], ....: [0, 0, b/2, oo, 0, 0, ], ....: [0, 0, 0, 0, oo, c/2,], ....: [0, 0, 0, 0, c/2, oo,], ....: ]) sage: R Cluster with 6 roots and 3 children sage: C = [r for r in R.children() if r.depth() == c/2][0] sage: A = [r for r in R.children() if r.depth() == a/2][0] sage: B = [r for r in R.children() if r.depth() == b/2][0] sage: T = R.BY_tree() sage: T BY tree with 1 yellow vertices, 3 blue vertices, 3 yellow edges, 0 blue edges sage: F = BYTreeIsomorphism(T, T, ....: lambda x: {A:A, B:B, C:C, R:R}[x], ....: lambda Y: 1) sage: T.tamagawa_number(F) a*b + a*c + b*c
Example 10.7:
sage: p = 7 sage: x = polygen(Qp(p, 200)) sage: w = 2 sage: a = 7 sage: u = 2 sage: z = 2 sage: f = ((x^(2)+1)^(2)-p^(u))*((x-1)^(2)-p^(z))*(x-p^(w / 2))*(x-p^(w / 2+2))*((x^(2)+p^(w+4))^(2)-p^(2*(w+4)+a)) sage: R = Cluster.from_polynomial(f) sage: T, F = R.BY_tree(with_frob=True) sage: F2 = BYTreeIsomorphism(T, T, F, lambda y:-1) sage: T.tamagawa_number(F2) == a*u*gcd(z, 2) True sage: p = 7 sage: x = polygen(Qp(p, 200)) sage: w = 6 sage: a = 12 sage: u = 2 sage: z = 3 sage: f = ((x^(2)+1)^(2)-p^(u))*((x-1)^(2)-p^(z))*(x-p^(w / 2))*(x-p^(w / 2+2))*((x^(2)+p^(w+4))^(2)-p^(2*(w+4)+a)) sage: R = Cluster.from_polynomial(f) sage: T, F = R.BY_tree(with_frob=True) sage: F2 = BYTreeIsomorphism(T, T, F, lambda y:-1) sage: T.tamagawa_number(F2) == a*u*gcd(z, 2) True sage: p = 7 sage: x = polygen(Qp(p, 200)) sage: w = 6 sage: a = 12 sage: u = 2 sage: z = 4 sage: f = ((x^(2)+1)^(2)-p^(u))*((x-1)^(2)-p^(z))*(x-p^(w / 2))*(x-p^(w / 2+2))*((x^(2)+p^(w+4))^(2)-p^(2*(w+4)+a)) sage: R = Cluster.from_polynomial(f) sage: T, F = R.BY_tree(with_frob=True) sage: F2 = BYTreeIsomorphism(T, T, F, lambda y:-1) sage: T.tamagawa_number(F2) == a*u*gcd(z, 2) True
- validate()¶
Checks if
self
is a valid BY tree, i.e. it is a tree, all vertices / edges are coloured blue or yellow, all edges have a positive weight, all vertices have nonnegative genus, and: (1) yellow vertices have genus 0, degree \ge 3, and only yellow edges; (2) blue vertices of genus 0 have at least one yellow edge; (3) at every vertex, 2g(v) + 2 \ge \# blue edges at v.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree, Cluster sage: T = BYTree() sage: T.add_blue_vertex('v1', 1) sage: T.add_blue_vertex('v2', 2) sage: T.add_yellow_vertex('v3') sage: T.add_yellow_vertex('v4') sage: T.add_yellow_edge(('v4', 'v1', 1)) sage: T.add_yellow_edge(('v4', 'v2', 1)) sage: T.add_blue_edge(('v3', 'v4', 2)) sage: T.validate() False
User guide section 10, example 10.4
sage: T = BYTree() sage: T.add_blue_vertex('v1', 1) sage: T.add_blue_vertex('v2', 0) sage: T.add_yellow_edge(('v1', 'v2', 2)) sage: T.validate() True
User guide section 10, example 10.5
sage: T = BYTree() sage: T.add_blue_vertex('v1') sage: T.add_blue_vertex('v2') sage: T.add_blue_vertex('v3') sage: T.add_yellow_vertex('v4') sage: T.add_blue_vertex('v5') sage: T.add_blue_vertex('v6') sage: T.add_blue_vertex('v7') sage: T.add_blue_vertex('v8') sage: T.add_yellow_edge(('v1', 'v4', 2)) sage: T.add_yellow_edge(('v2', 'v4', 2)) sage: T.add_yellow_edge(('v6', 'v4', 2)) sage: T.add_yellow_edge(('v7', 'v4', 2)) sage: T.add_blue_edge(('v7', 'v5', 2)) sage: T.add_yellow_edge(('v3', 'v5', 2)) sage: T.add_yellow_edge(('v8', 'v5', 2)) sage: T.validate() True sage: p = 3 sage: K = Qp(p) sage: C = Cluster.from_roots([K(1), K(p), K(2*p), K(2*p + p^2), K(2*p + 2*p^2), K(2*p + 2*p^2+p^3)]) sage: C.BY_tree().validate() True
- weight(v)¶
Return the weight of a vertex of
self
, defined by w: V\left(self\right) \rightarrow \mathbb{Z}w(v)=\left\{\begin{array}{ll}2 g(v)+2-\text { #blue edges at } v & \text { if } v \text { is blue, } \\ 0 & \text { if } v \text { is yellow }\end{array}\right.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster, BYTree sage: p = 11 sage: x = polygen(Qp(p, 200)) sage: R = Cluster.from_polynomial(p*(x^2 - p^5)*(x^3 - p^2)*((x-1)^3 - p^9)) sage: T = R.BY_tree() sage: s3 = R.children()[0] sage: s1 = R.children()[1].children()[3] sage: T.weight(s1) 2 sage: T.weight(s3) 3
- yellow_components()¶
Return the set of yellow components of
self
, i.e. the connected components ofself
\smallsetminusself.blue_subgraph()
, as a list of yellow edges in the component.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T.add_blue_vertex('v1', 1) sage: T.add_blue_vertex('v2', 0) sage: T.add_yellow_edge(('v1', 'v2', 2)) sage: T.yellow_components() [[('v1', 'v2', 2)]]
- yellow_edges()¶
Return the list of yellow edges of
self
.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T.add_blue_vertex('v1', 1) sage: T.add_blue_vertex('v2', 2) sage: T.add_yellow_vertex('v3') sage: T.add_yellow_vertex('v4') sage: T.add_yellow_edge(('v4', 'v1', 1)) sage: T.add_yellow_edge(('v4', 'v2', 1)) sage: T.add_blue_edge(('v3', 'v4', 2)) sage: T.yellow_edges() [('v1', 'v4', 1), ('v2', 'v4', 1)]
- yellow_vertices()¶
Return the list of yellow vertices of
self
.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree sage: T = BYTree() sage: T.add_blue_vertex('v1', 0) sage: T.add_yellow_vertex('v3') sage: T.add_blue_vertex('v2', 1) sage: T.add_yellow_vertex('v4') sage: T.yellow_vertices() ['v3', 'v4']
- class sage_cluster_pictures.cluster_pictures.BYTreeIsomorphism(A, B, f, eps)¶
Bases:
SageObject
Isomorphisms between BY trees, these are graph isomorphisms that preserve the BY tree structure, and additionally assign an sign to each yellow component of the tree.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree, BYTreeIsomorphism sage: T = BYTree() sage: T.add_blue_vertex('v1', 1) sage: T.add_blue_vertex('v2', 0) sage: T.add_yellow_edge(('v1', 'v2', 2)) sage: f = lambda v: {'v1':'v2','v2':'v1'}[v] sage: eps = lambda c: -1 sage: F = BYTreeIsomorphism(T, T, f, eps) sage: F BY tree isomorphism from BY tree with 0 yellow vertices, 2 blue vertices, 1 yellow edges, 0 blue edges to BY tree with 0 yellow vertices, 2 blue vertices, 1 yellow edges, 0 blue edges
- __call__(inp)¶
Return the image of the vertex or edge under
self
.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree, BYTreeIsomorphism sage: T = BYTree() sage: T.add_blue_vertex('v1', 1) sage: T.add_blue_vertex('v2', 0) sage: T.add_yellow_edge(('v1', 'v2', 2)) sage: f = lambda v: {'v1':'v2','v2':'v1'}[v] sage: eps = lambda c: -1 sage: F = BYTreeIsomorphism(T, T, f, eps) sage: F('v2') 'v1' sage: F('v1') 'v2' sage: F(T.edges(sort=False)[0]) ('v2', 'v1', 2)
- __init__(A, B, f, eps)¶
See
BYTree
for documentation.INPUT:
A
,B
- BY treesf
- a function from vertices ofA
to vertices ofB
,assumed to be bijective, preserve the colouring and genera, and that the induced map on edges preserves colouring.
eps
- a function from yellow components ofA
to \{\pm1\}.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree, BYTreeIsomorphism sage: T = BYTree() sage: T.add_blue_vertex('v1', 1) sage: T.add_blue_vertex('v2', 0) sage: T.add_yellow_edge(('v1', 'v2', 2)) sage: f = lambda v: {'v1':'v2','v2':'v1'}[v] sage: eps = lambda c: -1 sage: F = BYTreeIsomorphism(T, T, f, eps) sage: F BY tree isomorphism from BY tree with 0 yellow vertices, 2 blue vertices, 1 yellow edges, 0 blue edges to BY tree with 0 yellow vertices, 2 blue vertices, 1 yellow edges, 0 blue edges
- __weakref__¶
list of weak references to the object
- _repr_()¶
Return a string representation of
self
.OUTPUT:
a string
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree, BYTreeIsomorphism sage: T = BYTree() sage: T.add_blue_vertex('v1', 1) sage: T.add_blue_vertex('v2', 0) sage: T.add_yellow_edge(('v1', 'v2', 2)) sage: f = lambda v: {'v1':'v2','v2':'v1'}[v] sage: eps = lambda c: -1 sage: F = BYTreeIsomorphism(T, T, f, eps) sage: F BY tree isomorphism from BY tree with 0 yellow vertices, 2 blue vertices, 1 yellow edges, 0 blue edges to BY tree with 0 yellow vertices, 2 blue vertices, 1 yellow edges, 0 blue edges
- _test()¶
Check that
self
satisfies the properties assumed of it.
- codomain()¶
Return the codomain of
self
.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree, BYTreeIsomorphism sage: T = BYTree() sage: T.add_blue_vertex('v1', 1) sage: T.add_blue_vertex('v2', 0) sage: T.add_yellow_edge(('v1', 'v2', 2)) sage: f = lambda v: {'v1':'v2','v2':'v1'}[v] sage: eps = lambda c: -1 sage: F = BYTreeIsomorphism(T, T, f, eps) sage: F.codomain() BY tree with 0 yellow vertices, 2 blue vertices, 1 yellow edges, 0 blue edges
- domain()¶
Return the domain of
self
.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree, BYTreeIsomorphism sage: T = BYTree() sage: T.add_blue_vertex('v1', 1) sage: T.add_blue_vertex('v2', 0) sage: T.add_yellow_edge(('v1', 'v2', 2)) sage: f = lambda v: {'v1':'v2','v2':'v1'}[v] sage: eps = lambda c: -1 sage: F = BYTreeIsomorphism(T, T, f, eps) sage: F.domain() BY tree with 0 yellow vertices, 2 blue vertices, 1 yellow edges, 0 blue edges
- epsilon(inp)¶
Evaluate the sign function \epsilon associated to
self
at the componentinp
.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import BYTree, BYTreeIsomorphism sage: T = BYTree() sage: T.add_blue_vertex('v1', 1) sage: T.add_blue_vertex('v2', 0) sage: T.add_yellow_edge(('v1', 'v2', 2)) sage: f = lambda v: {'v1':'v2','v2':'v1'}[v] sage: eps = lambda c: -1 sage: F = BYTreeIsomorphism(T, T, f, eps) sage: F.epsilon(T.edges(sort=False)) -1 sage: F.epsilon(T.edges(sort=False)[0]) -1
- class sage_cluster_pictures.cluster_pictures.Cluster(M=[], parent=None, top=None, roots=None, depth=None, leading_coefficient=None)¶
Bases:
SageObject
Construct a cluster picture.
INPUT:
M
– a matrix of valuations of differences of roots
EXAMPLES:
Example 1.2 from M2D2:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 7 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve((x-1)*(x-(1+p^2))*(x-(1-p^2))*(x-p)*x*(x-p^3)*(x+p^3)) sage: C = Cluster.from_curve(H) sage: print(ascii_art(C)) ((* * *)_2 (* (* * *)_2)_1)_0
- BY_tree(with_frob=False, check=True)¶
Constructs the BY tree associated to the cluster picture, and optionally the associated
BYTreeIsomorphism
to Frobenius acting on the cluster.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster, BYTree sage: K = Qp(5) sage: R = Cluster.from_roots([K(1), K(6), K(2), K(7)]) sage: R.BY_tree() BY tree with 0 yellow vertices, 2 blue vertices, 1 yellow edges, 0 blue edges
Example 4.9 from the users guide:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(7,150) sage: x = polygen(K) sage: H = HyperellipticCurve((x^2+7^2)*(x^2-7^(15))*(x-7^6)*(x-7^6-7^9)) sage: R = Cluster.from_curve(H) sage: T = R.BY_tree() sage: T BY tree with 1 yellow vertices, 3 blue vertices, 3 yellow edges, 0 blue edges sage: sorted([e[2] for e in T.edges(sort=False)]) [3, 6, 10]
Example 4.11 from the users guide:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qq(11^3, 200, names="a") sage: a = K.gen() sage: z = K.teichmuller(10*a^2 + 7*a + 8) sage: x = polygen(K) sage: f = prod(x-a for a in [0,1,2,z-11,z+11,z^2 - 11, z^2 +11, z^4 -11, z^4 + 11]).map_coefficients(lambda x: x.trace()/3, new_base_ring=Qp(11, 200)) sage: H = HyperellipticCurve(f) sage: R = Cluster.from_curve(H) sage: T = R.BY_tree() sage: T BY tree with 0 yellow vertices, 4 blue vertices, 3 yellow edges, 0 blue edges sage: [e[2] for e in T.edges(sort=False)] [2, 2, 2] sage: sorted([T.genus(v) for v in T.vertices(sort=False)]) [0, 0, 0, 1]
- __eq__(other)¶
Return self==value.
- __hash__()¶
File: sage/structure/sage_object.pyx (starting at line 363)
Not implemented: mutable objects inherit from this class
EXAMPLES:
sage: hash(SageObject()) Traceback (most recent call last): ... TypeError: <... 'sage.structure.sage_object.SageObject'> is not hashable
- __init__(M=[], parent=None, top=None, roots=None, depth=None, leading_coefficient=None)¶
See
Cluster
for documentation.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: C = Cluster([\ [20, 2, 0],\ [2, 20, 0],\ [0, 0, 20],\ ]) sage: C Cluster with 3 roots and 2 children sage: C = Cluster(Matrix(ZZ, 4, 4,[\ [20, 1, 0, 0 ],\ [1, 20, 0, 0 ],\ [0, 0, 20, 1 ],\ [0, 0, 1, 20 ],\ ])) sage: C Cluster with 4 roots and 2 children sage: #TestSuite(C).run()
- __lt__(other)¶
Return self<value.
- __ne__(other)¶
Return self!=value.
- __weakref__¶
list of weak references to the object
- _ascii_art_()¶
Return an ascii art representation of
self
.EXAMPLES:
Example 3.7 from the users guide:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: x = polygen(K) sage: H = HyperellipticCurve(x*(x-1)*(x-2)*(x-3)*(x-5)*(x-8)*(x-13)) sage: R = Cluster.from_curve(H) sage: print(ascii_art(R)) (* * (* *)_1 (* * *)_1)_0 sage: p = 7 sage: K = Qp(p,150) sage: x = polygen(K) sage: H = HyperellipticCurve((x-1)*(x-2)*(x-p)*(x-2*p)*(x-3*p)*(x-4*p)) sage: R = Cluster.from_curve(H) sage: print(ascii_art(R)) (* * (* * * *)_1)_0 sage: H = HyperellipticCurve(H.hyperelliptic_polynomials()[0](1/x).numerator()) sage: R = Cluster.from_curve(H) sage: print(ascii_art(R)) (* * * * (* *)_1)_-1
- _latex_()¶
Return a LaTeX representation of
self
.OUTPUT:
a string
- _repr_()¶
Return a string representation of
self
.OUTPUT:
a string
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 7 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve((x-1)*(x-(1+p^2))*(x-(1-p^2))*(x-p)*x*(x-p^3)*(x+p^3)) sage: Cluster.from_curve(H) Cluster with 7 roots and 2 children
- _unicode_art_()¶
Return a unicode art representation of
self
.
- all_automorphisms()¶
Specialisation of
all_automorphisms()
toself = other
and always include roots.
- all_descendants()¶
Return (an iterator over) all descendent clusters of
self
(includingself
).EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(5), K(10), K(35), K(135)]) sage: list(C.all_descendants()) [Cluster with 5 roots and 2 children, Cluster with 1 roots and 0 children, Cluster with 4 roots and 2 children, Cluster with 1 roots and 0 children, Cluster with 3 roots and 2 children, Cluster with 1 roots and 0 children, Cluster with 2 roots and 2 children, Cluster with 1 roots and 0 children, Cluster with 1 roots and 0 children]
- all_isomorphisms(other, include_roots=False)¶
Construct all isomorphisms from
self
toother
. The parameter ‘include_roots’ indicates whether the clusters of size 1 are also considered.EXAMPLES:
Example with some symmetry:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: C = Cluster.from_picture('((* *)_1/2 (* *)_1/2 (* *)_1/2)_0') sage: isoms = C.all_isomorphisms(C) sage: isoms2 = C.all_isomorphisms(C, include_roots=True) sage: len(isoms) 6 sage: len(isoms2) 48
An example without depths:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: C = Cluster.from_picture('((* * *) (* * *))') sage: isoms = C.all_isomorphisms(C) sage: isoms2 = C.all_isomorphisms(C, include_roots=True) sage: len(isoms) 2 sage: len(isoms2) 72 sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: C = Cluster.from_picture('((* * *)_1 (* * *)_1/2)_0') sage: isoms = C.all_isomorphisms(C) sage: isoms2 = C.all_isomorphisms(C, include_roots=True) sage: len(isoms) 1 sage: len(isoms2) 36
- static ascii_to_lmfdb_label(s)¶
The lmfdb label of the cluster picture, this is defined only for clusters with depths as an alternative representation of the ascii_art.
c represents an opening bracket
~ is used in place of /
_ closes the previous open bracket and the following number (with negatives and possibly /) is the (relative) depth
a number in brackets denotes the number of roots there
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import * sage: Cluster.ascii_to_lmfdb_label("(● ● (● ● ●)_1/12 (● ● ● (● ●)_1)_1/12)_-1/6") 'c2c3_1~12c3c2_1_1~12_-1~6' sage: Cluster.ascii_to_lmfdb_label("(* * (* * *)_1/12 (* * * (* *)_1)_1/12)_-1/6") 'c2c3_1~12c3c2_1_1~12_-1~6'
- center()¶
A choice of center of
self
, i.e. some z_{\mathfrak{s}} \in K^{\mathrm{sep}} with \min _{r \in \mathfrak{s}} v\left(z_{\mathfrak{s}}-r\right)=d_{\mathfrak{s}}.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5) sage: C = Cluster(Matrix(ZZ, 4, 4,[\ [20, 1, 0, 0 ],\ [1, 20, 0, 0 ],\ [0, 0, 20, 1 ],\ [0, 0, 1, 20 ],\ ])) sage: C.roots() Traceback (most recent call last): ... AttributeError: This cluster does not have root information stored. sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.center() 0 sage: C.is_center(C.center()) True sage: C = Cluster.from_roots([K(1), K(2), K(10), K(35)]) sage: C.center() 0 sage: C.is_center(C.center()) True sage: K = Qp(7,150) sage: x = polygen(K) sage: H = HyperellipticCurve((x^2+7^2)*(x^2-7^(15))*(x-7^6)*(x-7^6-7^9)) sage: R = Cluster.from_curve(H) sage: a = R.children()[2] sage: t1 = a.children()[0] sage: t2 = a.children()[1] sage: R.is_center(R.center()) True sage: a.is_center(a.center()) True sage: t1.is_center(t1.center()) True sage: t2.is_center(t2.center()) True sage: R.center() 0 sage: a.center() 0 sage: t1.center() 0 sage: t2.center() == 7^6 True
- children()¶
Returns all children of
self
.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.children() [Cluster with 1 roots and 0 children, Cluster with 2 roots and 2 children]
- component_special_fibre()¶
Compute the component of the special fibre corresponding to
self
.EXAMPLES:
Example 6.9
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: x = polygen(Qp(5,150)) sage: H = HyperellipticCurve(x*((x+1)^2 - 5)*(x+4)*(x-6)) sage: R = Cluster.from_curve(H) sage: R.component_special_fibre() Hyperelliptic Curve over Finite Field of size 5 defined by y^2 = x^3 + 2*x^2 + x sage: R.red(5) 0
Example 6.10
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 5 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve((x^4-p^8)*(x^2+2*x+1-p^2)*(x^2-2*x+1-p)) sage: R = Cluster.from_curve(H) sage: R.component_special_fibre() Hyperelliptic Curve over Finite Field of size 5 defined by y^2 = x^2 + 3*x + 1 sage: R.children()[-1].component_special_fibre() Hyperelliptic Curve over Finite Field of size 5 defined by y^2 = x^4 + 4
- conductor_exponent()¶
Compute the conductor exponent of the Jacobian of the curve associated to
self
.EXAMPLES:
Lmfdb curve 2520.c.680400.1:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 5 sage: x = polygen(Qp(p, 200)) sage: R = Cluster.from_polynomial( -300*x^6 - 259*x^4 - 74*x^2 - 7) sage: R.conductor_exponent() 1
- curve_genus()¶
The genus of the curve on the generic fibre, g such that number of roots is 2g+1 or 2g+2.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.curve_genus() 1 sage: C = Cluster.from_roots([K(1), K(2), K(5), K(10), K(25)]) sage: C.curve_genus() 2 sage: C = Cluster.from_roots([K(1), K(2), K(5), K(10), K(25), K(50)]) sage: C.curve_genus() 2
- depth()¶
Return the depth of the cluster.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.depth() 0 sage: C = Cluster.from_roots([K(5), K(25), K(50)]) sage: C.depth() 1 sage: C = Cluster.from_roots([K(1), K(6), K(26), K(126)]) sage: C.children()[1].children()[1].depth() 3
Example 3.6 from the users guide:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(7,150) sage: x = polygen(K) sage: H = HyperellipticCurve((x^2+7^2)*(x^2-7^(15))*(x-7^6)*(x-7^6-7^9)) sage: R = Cluster.from_curve(H) sage: R.depth() 1 sage: R.children()[2].depth() 6 sage: R.children()[2].relative_depth() 5 sage: R.children()[2].children()[0].depth() 15/2 sage: R.children()[2].children()[1].depth() 9
- discriminant()¶
Computes the valuation of the discriminant of the curve. This is only implemented for semi-stable curves.
EXAMPLES:
Example 1.2 from M2D2:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 3 sage: x = polygen(Qp(p,200)) sage: R = Cluster.from_polynomial((x-1)*(x-(1+p^2))*(x-(1-p^2))*(x-p)*x*(x-p^3)*(x+p^3)) sage: R.discriminant() 36
Example 15.6:
sage: p = 11 sage: x = polygen(Qp(p, 200)) sage: C = Cluster.from_polynomial(p*(x^2-p^5)*(x^3-p^3)*((x-1)^3-p^9)) sage: C.discriminant() 55
Example 15.7:
sage: x = polygen(Qp(7,150)) sage: f = 7*(x^2+1)*(x^2+36)*(x^2+64) sage: C = Cluster.from_polynomial(f) sage: C.discriminant() 22
Lmfdb curve 336.a.172032.1:
sage: x = polygen(Qp(3, 200)) sage: C = Cluster.from_polynomial(-3*x^6 + 62*x^4 - 299*x^2 - 224) sage: C.discriminant() 1
- dual_graph(with_gal=False, check=True)¶
Constructs the dual graph of the special fibre of the minimal regular model associated to
self
.EXAMPLES:
Example 6.9
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: x = polygen(Qp(5,150)) sage: H = HyperellipticCurve(x*((x+1)^2 - 5)*(x+4)*(x-6)) sage: R = Cluster.from_curve(H) sage: R.dual_graph() Dual graph of Cluster with 5 roots and 3 children: Looped multi-graph on 2 vertices sage: len(R.dual_graph().edges(sort=False)) 3
Old example 6.6
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: x = polygen(Qp(3,150)) sage: H = HyperellipticCurve((x+5)*(x-4)*(x-13)*x*(x-3)*(x+4)) sage: R = Cluster.from_curve(H) sage: R.dual_graph() Dual graph of Cluster with 6 roots and 3 children: Looped multi-graph on 3 vertices
Old example 6.10
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 5 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve((x^4-p^8)*(x^2+2*x+1-p^2)*(x^2-2*x+1-p)) sage: R = Cluster.from_curve(H) sage: R.dual_graph() Dual graph of Cluster with 8 roots and 3 children: Looped multi-graph on 6 vertices
Example 1.2 from M2D2
sage: p = 3 sage: x = polygen(Qp(p,200)) sage: R = Cluster.from_polynomial((x-1)*(x-(1+p^2))*(x-(1-p^2))*(x-p)*x*(x-p^3)*(x+p^3)) sage: G = R.dual_graph() sage: G Dual graph of Cluster with 7 roots and 2 children: Looped multi-graph on 4 vertices sage: len(G.edges(sort=False)) 4
Example 8.4:
sage: p = 5 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve(x*(x-p)*(x-2*p)*(x-3*p)*(x-1)*(x-2)*(x-3)*(x-4)) sage: R = Cluster.from_curve(H) sage: G = R.dual_graph() sage: G Dual graph of Cluster with 8 roots and 5 children: Looped multi-graph on 2 vertices sage: len(G.edges(sort=False)) 2
Example 8.5:
sage: p = 5 sage: x = polygen(Qp(p,150)) sage: n = 3 sage: H = HyperellipticCurve((x-1)*(x-2)*(x-3)*(x-p^2)*(x-p^(n+2))*(x+p^(n+2))) sage: R = Cluster.from_curve(H) sage: G = R.dual_graph() sage: G # 2n + 1 vertices Dual graph of Cluster with 6 roots and 4 children: Looped multi-graph on 7 vertices sage: len(G.edges(sort=False)) == 2*n + 1 True sage: p = 7 sage: x = polygen(Qp(p,150)) sage: n = 1 sage: H = HyperellipticCurve((x-1)*(x-2)*(x-3)*(x-p^2)*(x-p^(n+2))*(x+p^(n+2))) sage: R = Cluster.from_curve(H) sage: G = R.dual_graph() sage: G # 2n + 1 vertices Dual graph of Cluster with 6 roots and 4 children: Looped multi-graph on 3 vertices sage: len(G.edges(sort=False)) == 2*n + 1 True sage: p = 7 sage: x = polygen(Qp(p,150)) sage: n = 5 sage: H = HyperellipticCurve((x-1)*(x-2)*(x-3)*(x-p^2)*(x-p^(n+2))*(x+p^(n+2))) sage: R = Cluster.from_curve(H) sage: G = R.dual_graph() sage: G # 2n + 1 vertices Dual graph of Cluster with 6 roots and 4 children: Looped multi-graph on 11 vertices sage: len(G.edges(sort=False)) == 2*n + 1 True
Example 13.7 (ii) (multiple twins)
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 23 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve(((x^2+1)^2 - 2*x^2*p^4 + 2*p^4 + p^8)*(x-2)*(x-3)) sage: C = Cluster.from_curve(H) sage: C.dual_graph() Dual graph of Cluster with 6 roots and 4 children: Looped multi-graph on 7 vertices
A non-principal top cluster:
sage: K = Qp(5,200) sage: x = polygen(K) sage: C = Cluster.from_polynomial((x-5)*x*(x-3)*(x-3-25)*(x-3-2*25)*(x-3-3*25)) sage: C Cluster with 6 roots and 2 children sage: C.dual_graph() Dual graph of Cluster with 6 roots and 2 children: Looped multi-graph on 6 vertices sage: C = Cluster.from_polynomial((x-15)*(x-10)*(x-5)*x*(x-3)*(x-3-25)*(x-3-2*25)*(x-3-3*25)) sage: C.dual_graph() Dual graph of Cluster with 8 roots and 2 children: Looped multi-graph on 6 vertices
Another test:
sage: K = Qp(3,200) sage: x = polygen(K) sage: C = Cluster.from_polynomial((x-1)*(x-6)*(x-5)*(x-10)*(x-19)*(x-28)) sage: G = C.dual_graph() sage: G Dual graph of Cluster with 6 roots and 3 children: Looped multi-graph on 2 vertices sage: len(G.edges(sort=False)) == 3 True
Plots:
- epsilon(sigma, sigmaK, frobenius_reduction=False)¶
\frac{\sigma\left(\theta_{s^{*}}\right)}{\theta_{\left(\sigma_{\mathfrak{s}}\right)^{*}}} \bmod \mathfrak{m} \in\{\pm 1\} \text { if } \mathfrak{s} \text { even or cotwin, } \epsilon_{\mathfrak{s}}(\sigma)=0 \text { otherwise }
INPUT:
sigma
an element of Galois acting on clusterssigmaK
an element of Galois as a map K \to Koptional parameter
frobenius_reduction
to force the calculation using reductions, assuming the action on the uniformiser is trvial
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5) sage: C = Cluster.from_roots([K(1), K(5), K(10)], leading_coefficient=1) sage: C.epsilon(lambda x: x, lambda x: x) 1 sage: C = Cluster.from_roots([K(1), K(2), K(10), K(35)], leading_coefficient=1) sage: C.children()[0].epsilon(lambda x: x, lambda x: x) 0
Example 3.7 from the users guide:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: x = polygen(K) sage: H = HyperellipticCurve(x*(x-1)*(x-2)*(x-3)*(x-8)) sage: R = Cluster.from_curve(H) sage: t = R.children()[-1] sage: t.epsilon(lambda x: x.frobenius(), R.field_frobenius()) 1
Example 4.11:
sage: K = Qq(11^3, 200, names="a") sage: a = K.gen() sage: z = K.teichmuller(10*a^2 + 7*a + 8) sage: x = polygen(K) sage: f = prod(x-a for a in [0,1,2,z-11,z+11,z^2 - 11, z^2 +11, z^4 -11, z^4 + 11]).map_coefficients(lambda x: x.trace()/3, new_base_ring=Qp(11, 200)) sage: H = HyperellipticCurve(f) sage: R = Cluster.from_curve(H) sage: t1 = R.children()[3] sage: t2 = R.children()[4] sage: t4 = R.children()[5] sage: # t1.center().frobenius() == t2.center() these are true in some order sage: # t2.center().frobenius() == t4.center() sage: # t4.center().frobenius() == t1.center() sage: #t1.epsilon(lambda x: x.frobenius(), R.field_frobenius()) 1 sage: # t2.epsilon(lambda x: x.frobenius(), R.field_frobenius()) 1 sage: # t4.epsilon(lambda x: x.frobenius(), R.field_frobenius()) -1
- field_frobenius()¶
Return the frobenius morphism of the base field of
self
.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: x = polygen(K) sage: C = Cluster.from_polynomial((x-1)*(x-6)*(x-26)*(x-126)) sage: C.field_frobenius() Identity endomorphism of 5-adic Field with capped relative precision 150 sage: C.children()[0].field_frobenius() Identity endomorphism of 5-adic Field with capped relative precision 150 sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(7,150) sage: x = polygen(K) sage: C = Cluster.from_polynomial((x^2+1)*(x-1)*x) sage: C.field_frobenius() Frobenius endomorphism on 7-adic Unramified Extension Field in b defined by x^2 + 6*x + 3 lifting b |--> b^7 on the residue field sage: C.children()[0].field_frobenius() Frobenius endomorphism on 7-adic Unramified Extension Field in b defined by x^2 + 6*x + 3 lifting b |--> b^7 on the residue field
- field_inertia()¶
Return the inertia morphism of the base field of
self
.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: x = polygen(K) sage: C = Cluster.from_polynomial((x-1)*(x-6)*(x-26)*(x-126)) sage: C.field_inertia() Identity endomorphism of 5-adic Field with capped relative precision 150
- frobenius()¶
The action of Frobenius.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: x = polygen(Qp(7,150)) sage: H = HyperellipticCurve((x^2 + 7^2)*(x^2 - 7^15)*(x - 7^6)*(x - 7^6 - 7^9)) sage: C = Cluster.from_curve(H) sage: C.children()[0].frobenius() == C.children()[1] True
Even if we have no roots the Galois action is sometimes implicit in the combinatorial structure of the cluster:
sage: C = Cluster.from_picture("(* (* *))") sage: C.frobenius() == C True sage: C.children()[0].frobenius() == C.children()[0] True sage: C.children()[1].frobenius() == C.children()[1] True sage: C = Cluster.from_picture("((* *)_1 (* *)_2)_0") sage: C.frobenius() == C True sage: C.children()[0].frobenius() == C.children()[0] True sage: C.children()[1].frobenius() == C.children()[1] True
If the cluster has root data this should be relatively fast:
sage: p = 7 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve(x^(12) + 36*x^(11) + 534*x^(10) + 4094*x^9 + 17667*x^8 + 44018*x^7 + 61093*x^6 + 44018*x^5 + 17667*x^4 + 4094*x^3 + 534*x^2 + 36*x + 1) sage: C = Cluster.from_curve(H) sage: C.children()[-1].frobenius() == C.children()[-1] True
- classmethod from_BY_tree(T, R)¶
Construct a Cluster from a (rooted) BY tree
EXAMPLES:
Going from cluster to tree and back is not a bijection:
sage: from sage_cluster_pictures.cluster_pictures import * sage: R = Cluster.from_picture("((* *)_4 *)_1") sage: T = R.BY_tree() sage: T BY tree with 0 yellow vertices, 2 blue vertices, 1 yellow edges, 0 blue edges sage: R2 = Cluster.from_BY_tree(T, R) sage: R2 Cluster with 4 roots and 3 children sage: T2 = R2.BY_tree() sage: T2 BY tree with 0 yellow vertices, 2 blue vertices, 1 yellow edges, 0 blue edges
- classmethod from_curve(H)¶
Construct a Cluster from a hyperelliptic curve.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 7 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve((x-1)*(x-(1+p^2))*(x-(1-p^2))*(x-p)*x*(x-p^3)*(x+p^3)) sage: Cluster.from_curve(H) Cluster with 7 roots and 2 children
- classmethod from_lmfdb_label(S)¶
Construct a Cluster from an lmfdb label.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import * sage: unicode_art(Cluster.from_lmfdb_label("c2c3c2_1_1~12c3_1~12_-1~6")) (● ● (● ● ●)_1/12 (● ● ● (● ●)_1)_1/12)_-1/6
- classmethod from_picture(S, leading_coefficient=None)¶
Construct a Cluster from an ascii art cluster picture with depths.
The recommended format is shown in the examples below, however the code will ignore all characters except digits brackets and asterisks, so extra annotations can be included but will currently be ignored.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: Cluster.from_picture("((* *)_1 *)_0") Cluster with 3 roots and 2 children
A slighly more complicated example:
sage: x = polygen(Qp(3)) sage: F = (1 + 2*3 + 2*3^2 + 2*3^3 + 3^4 + 2*3^6 + 2*3^7 + 3^8 + 2*3^9 + 3^11 + 3^12 + 3^15 + 2*3^16 + 2*3^19 + O(3^20))*x^6 + (2 + 3 + 2*3^2 + 3^3 + 2*3^4 + 2*3^5 + 3^6 + 2*3^8 + 3^9 + 2*3^10 + 2*3^11 + 3^12 + 3^13 + 3^15 + 3^16 + 2*3^17 + 2*3^19 + O(3^20))*x^5 + (3 + 2*3^2 + 2*3^3 + 2*3^4 + 3^6 + 3^7 + 3^10 + 3^12 + 2*3^13 + 2*3^14 + 3^15 + 3^16 + 2*3^17 + 3^18 + 3^19 + 3^20 + O(3^21))*x^4 + (3^3 + 2*3^4 + 3^6 + 2*3^10 + 2*3^11 + 3^12 + 3^13 + 3^14 + 2*3^15 + 2*3^16 + 3^18 + 3^19 + 2*3^20 + 2*3^21 + 2*3^22 + O(3^23))*x^3 + (2 + 3 + 3^2 + 2*3^3 + 3^4 + 2*3^7 + 3^9 + 3^11 + 3^12 + 3^13 + 2*3^14 + 2*3^15 + 3^16 + 2*3^17 + 2*3^18 + 2*3^19 + O(3^20))*x^2 + (3 + 2*3^2 + 3^3 + 3^4 + 3^5 + 2*3^6 + 2*3^7 + 3^8 + 2*3^9 + 3^10 + 3^11 + 3^12 + 3^13 + 2*3^14 + 3^15 + 3^16 + 2*3^17 + 2*3^18 + 3^19 + 3^20 + O(3^21))*x + 2 + 2*3^4 + 2*3^6 + 3^8 + 3^9 + 2*3^10 + 2*3^11 + 2*3^12 + 2*3^13 + 2*3^16 + 3^17 + 2*3^18 + 3^19 + O(3^20) sage: C = Cluster.from_polynomial(F) sage: ascii_art(C) (* * ((* *)_1/4 (* *)_1/4)_1/2)_0 sage: ascii_art(Cluster.from_picture(ascii_art(C))) (* * ((* *)_1/4 (* *)_1/4)_1/2)_0
Unicode input and output:
sage: unicode_art(Cluster.from_picture('(● ● ((● ●)_1/4 (● ●)_1/4)_1/2)_0')) (● ● ((● ●)_1/4 (● ●)_1/4)_1/2)_0
Negative valuations:
sage: ascii_art(Cluster.from_picture('(* (* *)_15/2)_-2')) (* (* *)_15/2)_-2
Without depths:
sage: ascii_art(Cluster.from_picture('(* (* *))')) (* (* *))
- classmethod from_polynomial(f, factors=None)¶
Construct a Cluster from a polynomial.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 7 sage: x = polygen(Qp(p,150)) sage: Cluster.from_polynomial((x-1)*(x-(1+p^2))*(x-(1-p^2))*(x-p)*x*(x-p^3)*(x+p^3)) Cluster with 7 roots and 2 children
- classmethod from_polynomial_without_roots(f, infinity=100000, factors=None)¶
Construct a Cluster from a polynomial without computing its root. This has the advantage that it also works for wild extensions, but you lose the root data.
NOTE:
The following input is currently broken
x = polygen(Zp(3)) F = (3 + 3^2 + 3^3 + 2*3^4 + 3^5 + 3^6 + 3^9 + 3^10 + 2*3^11 + 2*3^12 + 2*3^13 + 2*3^14 + 3^16 + 3^17 + 2*3^18 + O(3^21))*x^3 + (2*3^2 + 3^3 + 3^4 + 2*3^6 + 2*3^8 + 2*3^9 + 3^10 + 3^11 + 3^13 + 3^14 + 2*3^16 + 3^17 + 2*3^18 + O(3^22))*x^2 + (3 + 3^2 + 3^3 + 2*3^4 + 3^5 + 3^6 + 3^7 + 3^10 + 3^12 + 2*3^15 + 2*3^16 + 2*3^18 + 3^19 + 3^20 + O(3^21))*x + 3 + 3^2 + 3^3 + 3^4 + 3^5 + 2*3^6 + 2*3^7 + 3^8 + 2*3^11 + 3^12 + 3^13 + 3^14 + 3^15 + 3^17 + 2*3^18 + 3^19 + O(3^21) Cluster.from_polynomial_without_roots(F)
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 23 sage: x = polygen(Qp(p,200)) sage: f = x*(x-p^2)*(x-p)*(x-p-p^3)*(x-1)*(x-1-p^4)*(x-p-1)*(x-p-1-p^5) sage: Cluster.from_polynomial_without_roots(f)._ascii_art_() (((* *)_1 (* *)_2)_1 ((* *)_3 (* *)_4)_1)_0 sage: x = polygen(Qp(5,400)) sage: R = Cluster.from_polynomial_without_roots(x^5 + 256) sage: R Cluster with 5 roots and 5 children
- classmethod from_roots(roots, leading_coefficient=None, phi=None, rho=None)¶
Construct a Cluster from a list of roots.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5) sage: Cluster.from_roots([K(1), K(5), K(10)]) Cluster with 3 roots and 2 children
- genus()¶
The genus of
self
, g such that number of odd children is 2g+1 or 2g+2.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.genus() 0 sage: C = Cluster.from_roots([K(1), K(2), K(5), K(10), K(25)]) sage: C.genus() 1 sage: C = Cluster.from_roots([K(1), K(2), K(5), K(10), K(25), K(50)]) sage: C.genus() 0
- has_good_reduction(K)¶
Tests whether the curve associated to
self
has good reduction over K.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(3,150) sage: x = polygen(K) sage: H = HyperellipticCurve(x^6 - 27) sage: C = Cluster.from_curve(H) sage: C.has_good_reduction(K) False sage: H = HyperellipticCurve(x^3 + 1) sage: C = Cluster.from_curve(H) sage: C.has_good_reduction(K) False sage: H = HyperellipticCurve(x^3 + x + 1) sage: C = Cluster.from_curve(H) sage: C.has_good_reduction(K) True
- has_potentially_good_reduction()¶
Tests whether the curve associated to
self
has potentially good reduction.EXAMPLES:
Example 5.10
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: x = polygen(Qp(3,150)) sage: H = HyperellipticCurve(x^6 - 27) sage: C = Cluster.from_curve(H) sage: C.has_potentially_good_reduction() False
Example 5.8
sage: x = polygen(Qp(7,150)) sage: H = HyperellipticCurve((x^2 + 7^2)*(x^2 - 7^15)*(x - 7^6)*(x - 7^6 - 7^9)) sage: C = Cluster.from_curve(H) sage: C.has_potentially_good_reduction() False
- has_potentially_totally_toric_reduction()¶
Checks whether the curve associated to
self
’s Jacobian has potentially totally toric reduction.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: x = polygen(Qp(7,150)) sage: H = HyperellipticCurve((x^2 + 7^2)*(x^2 - 7^15)*(x - 7^6)*(x - 7^6 - 7^9)) sage: C = Cluster.from_curve(H) sage: C.has_potentially_totally_toric_reduction() True
- homology_of_special_fibre()¶
Computes H1 together with a Frobenius action if possible
EXAMPLES:
TODO what is this example 13.7 (ii) not sure on correctness:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 23 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve(((x^2+1)^2 - 2*x^2*p^4 + 2*p^4 + p^8)*(x-2)*(x-3)) sage: C = Cluster.from_curve(H) sage: H1, M, frob = C.homology_of_special_fibre() #TODO check M sage: L = [b for b in H1.basis()] sage: frob(L[0]) == -L[1] True sage: frob(L[1]) == -L[0] True
Example 8.4:
sage: p = 5 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve(x*(x-p)*(x-2*p)*(x-3*p)*(x-1)*(x-2)*(x-3)*(x-4)) sage: R = Cluster.from_curve(H) sage: s = R.children()[-1] sage: H1, M, frob = R.homology_of_special_fibre() sage: H1 Free module generated by {Cluster with 4 roots and 4 children} over Integer Ring sage: M [2] sage: L = next(b for b in H1.basis()) sage: frob(L) == L True sage: p = 7 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve(x*(x-p)*(x-2*p)*(x-3*p)*(x-1)*(x-2)*(x-3)*(x-4)) sage: R = Cluster.from_curve(H) sage: s = R.children()[-1] sage: H1, M, frob = R.homology_of_special_fibre() sage: H1 Free module generated by {Cluster with 4 roots and 4 children} over Integer Ring sage: M [2] sage: L = next(b for b in H1.basis()) sage: frob(L) == -L True
Example 8.5:
sage: p = 5 sage: x = polygen(Qp(p,150)) sage: n = 3 sage: H = HyperellipticCurve((x-1)*(x-2)*(x-3)*(x-p^2)*(x-p^(n+2))*(x+p^(n+2))) sage: R = Cluster.from_curve(H) sage: R.homology_of_special_fibre() # TODO double check lengths (Free module generated by {Cluster with 2 roots and 2 children} over Integer Ring, [6], Generic endomorphism of Free module generated by {Cluster with 2 roots and 2 children} over Integer Ring) sage: p = 7 sage: x = polygen(Qp(p,150)) sage: n = 1 sage: H = HyperellipticCurve((x-1)*(x-2)*(x-3)*(x-p^2)*(x-p^(n+2))*(x+p^(n+2))) sage: R = Cluster.from_curve(H) sage: R.homology_of_special_fibre() (Free module generated by {Cluster with 2 roots and 2 children} over Integer Ring, [2], Generic endomorphism of Free module generated by {Cluster with 2 roots and 2 children} over Integer Ring) sage: p = 7 sage: x = polygen(Qp(p,150)) sage: n = 5 sage: H = HyperellipticCurve((x-1)*(x-2)*(x-3)*(x-p^2)*(x-p^(n+2))*(x+p^(n+2))) sage: R = Cluster.from_curve(H) sage: R.homology_of_special_fibre() (Free module generated by {Cluster with 2 roots and 2 children} over Integer Ring, [10], Generic endomorphism of Free module generated by {Cluster with 2 roots and 2 children} over Integer Ring)
Example 8.6:
sage: p = 7 sage: x = polygen(Qp(p,150)) sage: a = 1 sage: b = 2 sage: c = 2 sage: H = HyperellipticCurve((x^2-p^a)*((x-1)^2-p^b)*(x^2*p^c - 1)) sage: R = Cluster.from_curve(H) sage: H, M, frob = R.homology_of_special_fibre() sage: H Free module generated by {Cluster with 2 roots and 2 children, Cluster with 2 roots and 2 children} over Integer Ring sage: M [3 2] [2 4] sage: L = [b for b in H.basis()] sage: frob(L[0]) == -L[0] True sage: frob(L[1]) == -L[1] True sage: p = 5 sage: x = polygen(Qp(p,150)) sage: a = 3 sage: b = 1 sage: c = 3 sage: H = HyperellipticCurve((x^2-p^a)*((x-1)^2-p^b)*(x^2*p^c - 1)) sage: R = Cluster.from_curve(H) sage: H, M, frob = R.homology_of_special_fibre() sage: H Free module generated by {Cluster with 2 roots and 2 children, Cluster with 2 roots and 2 children} over Integer Ring sage: M [4 3] [3 6] sage: L = [b for b in H.basis()] sage: frob(L[0]) == L[0] True sage: frob(L[1]) == L[1] True
Check that Lmfdb curve 196.a.21952.1 completes:
sage: K = Qp(7,200) sage: x = polygen(K) sage: H = HyperellipticCurve(x.parent()([4, 12, 25, 30, 25, 12, 4])) sage: R = Cluster.from_curve(H) sage: R.homology_of_special_fibre() ( [2 1] Free module generated by {0, 1} over Integer Ring, [1 2], Generic endomorphism of Free module generated by {0, 1} over Integer Ring )
- inertia()¶
The action of a generator of the inertia group.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: x = polygen(Qp(7,150)) sage: H = HyperellipticCurve((x^2 + 7^2)*(x^2 - 7^15)*(x - 7^6)*(x - 7^6 - 7^9)) sage: C = Cluster.from_curve(H) sage: C.children()[0].inertia() == C.children()[1] False
If the cluster has root data this should be relatively fast:
sage: p = 7 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve(x^(12) + 36*x^(11) + 534*x^(10) + 4094*x^9 + 17667*x^8 + 44018*x^7 + 61093*x^6 + 44018*x^5 + 17667*x^4 + 4094*x^3 + 534*x^2 + 36*x + 1) sage: C = Cluster.from_curve(H) sage: C.children()[-1].inertia() == C.children()[-1] True
- integral_determinant_valuation()¶
v\left(\frac{\omega^{\circ}}{\omega}\right)
EXAMPLES:
Example 14.8:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 7 sage: x = polygen(Qp(p, 200)) sage: R = Cluster.from_polynomial(((x-7^2)^2+1)*((x-2 * 7^2)^2+1)*((x-3 * 7^2)^2+1)*(x^2-1)) sage: R.integral_determinant_valuation() 2
Example 14.9:
sage: p = 7 sage: x = polygen(Qp(p, 200)) sage: f = 7^2*(x^6 - 1) sage: n = 1 sage: R = Cluster.from_polynomial(7^(6*n)*f(x/7^n)) sage: R.integral_determinant_valuation() 5 sage: n = 2 sage: R = Cluster.from_polynomial(7^(6*n)*f(x/7^n)) sage: R.integral_determinant_valuation() 8
Kunzweiler: Differential forms example 1.5 (slightly corrected equation):
sage: p = 5 sage: x = polygen(Qp(p, 300)) sage: R = Cluster.from_polynomial(x*(x-p^6)*(x-2*p^6)*(x-p^4)*(x-2*p^4)*(x-3*p^4)*(x-1)*(x-1-p^8)*(x-1-2*p^8)*(x-1-3*p^8)*(x-2)*(x-3)) sage: R.integral_determinant_valuation() 21
Only works for semistable curves
sage: p = 13 sage: x = polygen(Qp(p, 300)) sage: R = Cluster.from_polynomial(x^6 + 4*x^5 + 6*x^4 + 2*x^3 + x^2 + 2*x + 1) sage: R.integral_determinant_valuation() Traceback (most recent call last): ... NotImplementedError
- integral_differential_lattice()¶
(\omega^{\circ}_i)_i as a lattice inside the standard basis differentials (x^i \mathrm d x/ y)_i.
EXAMPLES:
Example 14.8:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 7 sage: x = polygen(Qp(p, 200)) sage: R = Cluster.from_polynomial(((x-7^2)^2+1)*((x-2 * 7^2)^2+1)*((x-3 * 7^2)^2+1)*(x^2-1)) sage: R.integral_differential_lattice() [2*7 + O(7^201) 0 0] [ O(7^197) 2*7 + O(7^201) 0] [ 2 + O(7^196) 0 2 + O(7^200)]
Example 14.9:
sage: p = 7 sage: x = polygen(Qp(p, 200)) sage: f = 7^2*(x^6 - 1) sage: n = 1 sage: R = Cluster.from_polynomial(7^(6*n)*f(x/7^n)) sage: R.integral_differential_lattice() [7^3 + O(7^203) 0] [ 0 7^2 + O(7^202)] sage: n = 2 sage: R = Cluster.from_polynomial(7^(6*n)*f(x/7^n)) sage: R.integral_differential_lattice() [7^5 + O(7^205) 0] [ 0 7^3 + O(7^203)]
Kunzweiler: Differential forms example 1.5 (slightly corrected equation):
sage: p = 5 sage: x = polygen(Qp(p, 300)) sage: R = Cluster.from_polynomial(x*(x-p^6)*(x-2*p^6)*(x-p^4)*(x-2*p^4)*(x-3*p^4)*(x-1)*(x-1-p^8)*(x-1-2*p^8)*(x-1-3*p^8)*(x-2)*(x-3)) sage: R.integral_differential_lattice().determinant() 5^21 + O(5^321)
Only works for semistable curves
sage: p = 13 sage: x = polygen(Qp(p, 300)) sage: R = Cluster.from_polynomial(x^6 + 4*x^5 + 6*x^4 + 2*x^3 + x^2 + 2*x + 1) sage: R.integral_differential_lattice() Traceback (most recent call last): ... NotImplementedError
- is_center(z)¶
Checks if a point z is a center of the cluster, i.e. \min_{r\in self}v(z-r) = ` ``self.depth()`
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.is_center(C.center()) True sage: C = Cluster.from_roots([K(1), K(2), K(10), K(35)]) sage: C.is_center(K(1/5)) False sage: C = Cluster.from_roots([K(1)]) sage: C.is_center(K(1 + 5)) False
TESTS:
sage: p = 5 sage: K = Qp(p,150) sage: x = polygen(K) sage: C = Cluster.from_polynomial((x-1)*(x-(1+p^2))*(x-(1-p^2))*(x-p)*x*(x-p^3)*(x+p^3)) sage: for s in C.all_descendants(): ....: assert s.is_center(s.center())
- is_cotwin()¶
Check if
self
is a cotwin.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.is_cotwin() True sage: C.children()[0].is_cotwin() False sage: C.children()[1].is_cotwin() False sage: C = Cluster.from_roots([K(1), K(5), K(10), K(35)]) sage: C.is_cotwin() False sage: C.children()[0].is_cotwin() False sage: C.children()[1].is_cotwin() True sage: C = Cluster.from_roots([K(1), K(2), K(10), K(35)]) sage: C.is_cotwin() True sage: C.children()[0].is_cotwin() False sage: C.children()[1].is_cotwin() False
- is_even()¶
Check if
self
is even.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.is_even() False sage: C = Cluster.from_roots([K(1), K(2), K(5), K(10)]) sage: C.is_even() True sage: C = Cluster.from_roots([K(1), K(6), K(5), K(10)]) sage: C.is_even() True
- is_minimal()¶
Return whether or not the defining equation corresponding to
self
is minimal. Theorem 16.2 and 16.3 in the users guide.EXAMPLES:
Example 16.5:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 5 sage: x = polygen(Qp(p, 200)) sage: R = Cluster.from_polynomial((x^2-1)*(x^3-p)*((x-2)^3 - p^7)) sage: R.is_minimal() True
Example 16.6:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 7 sage: x = polygen(Qp(p, 200)) sage: R = Cluster.from_polynomial(p^2*(x-1/p^2)*(x^5-1)) sage: R.is_minimal() True
Example 16.7:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 11 sage: x = polygen(Qp(p, 200)) sage: R = Cluster.from_polynomial((x^3-p^15)*(x^2-p^6)*(x^3 - p^3)) sage: R.is_minimal() False sage: R = Cluster.from_polynomial(((x^3-p^15)*(x^2-p^6)*(x^3 - p^3))(p^3*x)/p^18) sage: R.is_minimal() True
Random examples:
sage: p = 5 sage: x = polygen(Qp(p, 200)) sage: R = Cluster.from_polynomial((x-1)*(x-2)*(x-3)) sage: R.is_minimal() True
- is_odd()¶
Check if
self
is odd.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.is_odd() True sage: C = Cluster.from_roots([K(1), K(2), K(5), K(10)]) sage: C.is_odd() False sage: C = Cluster.from_roots([K(1), K(6), K(5), K(10)]) sage: C.is_odd() False
- is_principal()¶
Check if
self
is principal, i.e. if |\mathfrak{s}|\ne 2 g+2 it is proper, not a twin or a cotwin and if |\mathfrak{s}|=2 g+2 then \mathfrak{s} has \geq 3 children.EXAMPLES:
Not-proper:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(3,150) sage: C = Cluster.from_roots([K(1), K(3), K(6)]) sage: C.children()[0].is_principal() False
Cotwins:
sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(5), K(10), K(35)]) sage: C.children()[1].is_principal() False sage: C = Cluster.from_roots([K(1), K(2), K(10), K(35)]) sage: C.is_principal() False sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.is_principal() False
A twin:
sage: C.children()[1].is_principal() False
Not enough children:
sage: C = Cluster.from_roots([K(1), K(6), K(5), K(10)]) sage: C.is_principal() False
Example 3.6 from the users guide:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(7,150) sage: x = polygen(K) sage: H = HyperellipticCurve((x^2+7^2)*(x^2-7^(15))*(x-7^6)*(x-7^6-7^9)) sage: R = Cluster.from_curve(H) sage: R.is_principal() False sage: a = R.children()[2] sage: a.is_principal() True sage: all(not t.is_principal() for t in R.all_descendants() if t != a and t != R) True
- is_proper()¶
Returns whether or not
self
is proper, i.e. has size at least 2.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.is_proper() True sage: C.children()[1].is_proper() True sage: C.children()[0].is_proper() False
- is_semistable(K)¶
Tests whether the curve associated to
self
is semi-stable over K.EXAMPLES:
Example 5.8
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: x = polygen(Qp(7,150)) sage: H = HyperellipticCurve((x^2 + 7^2)*(x^2 - 7^15)*(x - 7^6)*(x - 7^6 - 7^9)) sage: C = Cluster.from_curve(H) sage: C.is_semistable(Qp(7)) True
Example 5.10:
sage: x = polygen(Qp(3,150)) sage: H = HyperellipticCurve(x^6 - 27) sage: C = Cluster.from_curve(H) sage: C.is_semistable(Qp(3)) False
We don’t need roots necessarily and it doesn’t matter the field:
sage: C = Cluster.from_picture("((* * *)_1/2 *)_0") sage: C.is_semistable(Qp(5)) False
We still don’t need roots, just a leading coefficient in some cases:
sage: C = Cluster.from_picture("(* * *)_0", leading_coefficient=Qp(5)(5)) sage: C.is_semistable(Qp(5)) False
- is_top_cluster()¶
Check if
self
is the top cluster for the picture.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.is_top_cluster() True sage: C.children()[0].is_top_cluster() False
- is_translation_integral()¶
Return whether or not the curve corresponding to
self
is integral (up to translation of x). Theorem 16.1 in the users guide.EXAMPLES:
Example 16.4:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 5 sage: x = polygen(Qp(p, 200)) sage: R = Cluster.from_polynomial(p*(x-1/p^2)*((x-1/p^2)^3 - p^9)*(x-1/p^2 - 1/p)) sage: R.is_translation_integral() True
Random examples:
sage: p = 5 sage: x = polygen(Qp(p, 200)) sage: R = Cluster.from_polynomial((x-1)*(x-2)*(x-3)) sage: R.is_translation_integral() True sage: p = 5 sage: x = polygen(Qp(p, 200)) sage: R = Cluster.from_polynomial((x-1)*(x^2-1/p)) sage: R.is_translation_integral() False
- is_twin()¶
Check if
self
is a twin.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.is_twin() False sage: C.children()[0].is_twin() False sage: C.children()[1].is_twin() True
- is_ubereven()¶
Check if
self
is übereven.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.is_ubereven() False sage: C.children()[0].is_ubereven() False sage: C.children()[1].is_ubereven() False sage: C = Cluster.from_roots([K(1), K(2), K(5), K(10)]) sage: C.is_ubereven() False sage: C = Cluster.from_roots([K(1), K(6), K(5), K(10)]) sage: C.is_ubereven() True
- jacobian_has_good_reduction(K)¶
Tests whether the curve associated to
self
’s Jacobian has good reduction over K.EXAMPLES:
Example 5.10
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(3,150) sage: x = polygen(K) sage: H = HyperellipticCurve(x^6 - 27) sage: C = Cluster.from_curve(H) sage: C.jacobian_has_good_reduction(K) False
- jacobian_has_potentially_good_reduction()¶
Test whether the curve associated to
self
’s Jacobian has potentially good reduction.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: x = polygen(Qp(3,150)) sage: H = HyperellipticCurve(x^6 - 27) sage: C = Cluster.from_curve(H) sage: C.jacobian_has_potentially_good_reduction() True
- lambda_tilde()¶
Computes the \tilde\lambda of
self
(see section 3)\tilde\lambda(\mathfrak s) = \frac{1}{2}\left(v(c)+|\tilde{\mathfrak{s}}| d_{\mathfrak{s}}+\sum_{r \notin \mathfrak{s}} d_{\mathfrak{s} \wedge r}\right)
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 7 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve(x^3-p^5) sage: C = Cluster.from_curve(H) sage: C.lambda_tilde() 5/2 sage: x = polygen(Qp(7,150)) sage: H = HyperellipticCurve(x*(x^6-21*x^4-1911*x^2-21952)) sage: C = Cluster.from_curve(H) sage: C.lambda_tilde() 3/4 sage: C.children()[1].lambda_tilde() 9/4 sage: C.children()[1].lambda_tilde() 9/4
Example 12.6
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 5 sage: x = polygen(Qp(p, 150)) sage: R = Cluster.from_polynomial_without_roots(x^5+256) sage: R.lambda_tilde() 5/8
Example 12.7
sage: x = polygen(Qp(7,150)) sage: H = HyperellipticCurve((x^4 - 7)*(x-1)) sage: C = Cluster.from_curve(H) sage: C.lambda_tilde() 0 sage: C.children()[1].lambda_tilde() 1/2
Example 12.8
sage: x = polygen(Qp(97,150)) sage: H = HyperellipticCurve((x^3 - 97)*(x-1)*(x-2)*(x-3)) sage: C = Cluster.from_curve(H) sage: C.lambda_tilde() 0 sage: C.children()[3].lambda_tilde() 1/2
An example without roots (but with a leading coefficient still):
sage: C = Cluster.from_picture("(* (* *)_2)_1", leading_coefficient = Qp(5)(25)) sage: C.lambda_tilde() 3/2
- leading_coefficient()¶
Return the leading coefficient of the polynomial defining this cluster.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 5 sage: K = Qp(p,150) sage: x = polygen(K) sage: H = HyperellipticCurve(2*(x-1)*(x-(1+p^2))*(x-(1-p^2))*(x-p)*x*(x-p^3)*(x+p^3)) sage: C = Cluster.from_curve(H) sage: C.leading_coefficient() 2 + O(5^150) sage: C = Cluster.from_roots([K(1), K(6), K(26), K(126)]) sage: C.leading_coefficient() Traceback (most recent call last): ... AttributeError: This cluster does not have a leading coefficient stored. sage: C = Cluster(Matrix(ZZ, 4, 4,[\ [20, 1, 0, 0 ],\ [1, 20, 0, 0 ],\ [0, 0, 20, 1 ],\ [0, 0, 1, 20 ],\ ])) sage: C.leading_coefficient() Traceback (most recent call last): ... AttributeError: This cluster does not have a leading coefficient stored. sage: C = Cluster.from_roots([K(1), K(6), K(26), K(126)], leading_coefficient=1) sage: C.leading_coefficient() 1
- lmfdb_label()¶
Return the lmfdb label of
self
.
- meet(other)¶
Construct
self
\wedgeother
.EXAMPLES:
Example 3.6 from the users guide:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(7,150) sage: x = polygen(K) sage: H = HyperellipticCurve((x^2+7^2)*(x^2-7^(15))*(x-7^6)*(x-7^6-7^9)) sage: R = Cluster.from_curve(H) sage: a = R.children()[2] sage: t1 = a.children()[0] sage: t2 = a.children()[1] sage: t1.meet(t2) == a True sage: t1.meet(a) == a True sage: t1.meet(R.children()[1]) == R True
- minimal_discriminant()¶
Computes the valuation of the minimal discriminant of the curve. This is only implemented for semi-stable curves.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: x = polygen(Qp(7,150)) sage: f = (x^3 - 7^15)*(x^2-7^6)*(x^3-7^3) sage: Cluster.from_polynomial(f).minimal_discriminant() 24
Example 15.7:
sage: f = 7*(x^2+1)*(x^2+36)*(x^2+64) sage: Cluster.from_polynomial(f).minimal_discriminant() 22 sage: #x = polygen(Qq(7^2,150,names="t")) sage: #f = 7*(x^2+1)*(x^2+36)*(x^2+64) sage: #Cluster.from_polynomial(f).minimal_discriminant()
Example 15.6:
sage: p = 11 sage: x = polygen(Qp(p, 200)) sage: C = Cluster.from_polynomial(p*(x^2-p^5)*(x^3-p^3)*((x-1)^3-p^9)) sage: C.minimal_discriminant() 27
- n_tame()¶
EXAMPLES:
Example 12.5
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 3 sage: x = polygen(Qp(p)) sage: R = Cluster.from_polynomial((x^2-p^2)*((x-1)^2-p^2)*((x-2)^2-p^2)) sage: R.n_tame() 2
Example 12.6
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 5 sage: x = polygen(Qp(p, 150)) sage: R = Cluster.from_polynomial_without_roots(x^5+256) sage: R.n_tame() 4
Example 12.7
sage: x = polygen(Qp(7)) sage: R = Cluster.from_polynomial(x^5+5*x^4+40*x^3+80*x^2+256*x) sage: R.n_tame() 3
Example 12.8
sage: x = polygen(Qp(97,150)) sage: H = HyperellipticCurve((x^3 - 97)*(x-1)*(x-2)*(x-3)) sage: C = Cluster.from_curve(H) sage: C.n_tame() 2
Example 1.2 from M2D2:
sage: p = 3 sage: x = polygen(Qp(p,200)) sage: R = Cluster.from_polynomial((x-1)*(x-(1+p^2))*(x-(1-p^2))*(x-p)*x*(x-p^3)*(x+p^3)) sage: R.n_tame() 1
- n_wild()¶
The wild component of the conductor exponent.
EXAMPLES:
Lmfdb curve 249.a.249.1:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 3 sage: x = polygen(Qp(p)) sage: R = Cluster.from_polynomial(x^6 + 2*x^3 + 4*x^2 + 4*x + 1) sage: R.n_tame() 1 sage: R.n_wild() #should be 0 0
Example 12.5
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 3 sage: x = polygen(Qp(p)) sage: R = Cluster.from_polynomial((x^2-p^2)*((x-1)^2-p^2)*((x-2)^2-p^2)) sage: R.n_wild() 0
Lmfdb curve 360.a.6480.1:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 5 sage: x = polygen(Qp(p)) sage: R = Cluster.from_polynomial(x^6 - 10*x^4 + 29*x^2 - 20) sage: R.n_tame() 1 sage: R.n_wild() 0
- nu()¶
Computes the \nu of
self
(see section 3)EXAMPLES:
Example 5.8
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: x = polygen(Qp(7,150)) sage: H = HyperellipticCurve((x^2 + 7^2)*(x^2 - 7^15)*(x - 7^6)*(x - 7^6 - 7^9)) sage: C = Cluster.from_curve(H) sage: C.children()[2].nu() 26
Example 5.10
sage: x = polygen(Qp(3,150)) sage: H = HyperellipticCurve(x^6 - 27) sage: C = Cluster.from_curve(H) sage: C.children()[0].nu() 9/2
Other
sage: p = 7 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve(x^3-p^5) sage: C = Cluster.from_curve(H) sage: C.nu() 5 sage: x = polygen(Qp(7,150)) sage: H = HyperellipticCurve(((x-7^2)^2+1)*((x-2*7^2)^2+1)*((x-3*7^2)^2+1)*(x^2-1)) sage: C = Cluster.from_curve(H) sage: C.nu() 0 sage: C.children()[2].nu() 6 sage: C.children()[3].nu() 6
An example without roots (but with a leading coefficient still):
sage: C = Cluster.from_picture("(* (* *)_2)_1", leading_coefficient = Qp(5)(25)) sage: C.nu() 5
- parent_cluster()¶
Return the parent cluster of
self
.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(6), K(26), K(126)]) sage: C.children()[1].children()[1].children()[1].parent_cluster().parent_cluster() Cluster with 3 roots and 2 children
- potential_toric_rank()¶
Computes the potential toric rank of the Jacobian of the curve.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: x = polygen(Qp(3,150)) sage: H = HyperellipticCurve(x^6 - 27) sage: C = Cluster.from_curve(H) sage: C.potential_toric_rank() 0 sage: C = Cluster.from_picture('(* (* *))') sage: C.potential_toric_rank() 1 sage: C = Cluster.from_picture('(* * *)') sage: C.potential_toric_rank() 0
- red(x, check=True)¶
Compute the reduction of a point to the component corresponding to
self
.EXAMPLES:
Example 6.9
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: x = polygen(Qp(5,150)) sage: H = HyperellipticCurve(x*((x+1)^2 - 5)*(x+4)*(x-6)) sage: R = Cluster.from_curve(H) sage: R.red(1) 1 sage: R.red(5) 0
Old example 6.6
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: x = polygen(Qp(3,150)) sage: H = HyperellipticCurve((x+5)*(x-4)*(x-13)*x*(x-3)*(x+4)) sage: R = Cluster.from_curve(H) sage: R.red(1) 1 sage: R.red(5) 2
Example 6.10
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 5 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve((x^4-p^8)*(x^2+2*x+1-p^2)*(x^2-2*x+1-p)) sage: R = Cluster.from_curve(H) sage: R.red(2) 2 sage: R.red(H.lift_x(2)) (2 : 1 : 1) sage: R.red(H.lift_x(3)) (3 : 2 : 1)
- relative_depth()¶
Return the depth of the cluster.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.relative_depth() 0 sage: C.children()[1].relative_depth() 1 sage: C = Cluster.from_roots([K(5), K(25), K(50)]) sage: C.relative_depth() 1 sage: C.children()[1].relative_depth() 1 sage: C = Cluster.from_roots([K(1), K(6), K(26), K(126)]) sage: C.children()[1].children()[1].relative_depth() 1
- root_number()¶
Computes the root number of
self
.EXAMPLES:
Example 13.7 (i)
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 23 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve(((x-1)^2 - p^4)*(x^2 - p^4)*(x-2)*(x-3)) sage: C = Cluster.from_curve(H) sage: C.root_number() 1
Example 13.7 (ii)
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 23 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve(((x^2+1)^2 - 2*p^4*x^2 + 2*p^4+ p^8)*(x-2)*(x-3)) sage: C = Cluster.from_curve(H) sage: C.root_number() -1
Example 13.7 (iii)
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 23 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve(-(x^2 - p^4)*((x-1)^2 - p^4)*(x-2)*(x-3)) sage: C = Cluster.from_curve(H) sage: C.root_number() 1
Example 13.8
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 7 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve(p*(x^2-p^5)*((x-1)^2-p^5)*((x-2)^2-p^5)) sage: C = Cluster.from_curve(H) sage: C.root_number() # 1 Traceback (most recent call last): ... NotImplementedError: Cluster is not semi-stable
Example 13.9
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 7 sage: x = polygen(Qp(p,150)) sage: H = HyperellipticCurve((x^3-p^8)*(x-1)*((x-1)^2-p^p)) sage: C = Cluster.from_curve(H) sage: C.root_number() # -1 Traceback (most recent call last): ... NotImplementedError: Cluster is not semi-stable
Lmfdb curve 1503.a.4509.1
sage: K = Qp(3,200) sage: x = polygen(K) sage: H = HyperellipticCurve(x^6 + 4*x^5 - 2*x^4 - 10*x^3 + x^2 + 6*x + 1) sage: R3 = Cluster.from_curve(H) sage: K = Qp(167,200) sage: x = polygen(K) sage: H = HyperellipticCurve(x^6 + 4*x^5 - 2*x^4 - 10*x^3 + x^2 + 6*x + 1) sage: R167 = Cluster.from_curve(H) sage: R3.root_number()*R167.root_number() -1
Lmfdb curve 363.a.43923.1
sage: K = Qp(3,200) sage: x = polygen(K) sage: H = HyperellipticCurve(44*x^5 - 51*x^4 - 28*x^3 + 40*x^2 + 4*x - 8) sage: R3 = Cluster.from_curve(H) sage: K = Qp(11,200) sage: x = polygen(K) sage: H = HyperellipticCurve(44*x^5 - 51*x^4 - 28*x^3 + 40*x^2 + 4*x - 8) sage: R11 = Cluster.from_curve(H) sage: R11.root_number()*R3.root_number() 1
- roots()¶
Return the list of roots in this cluster.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(6), K(26), K(126)]) sage: C.roots() [1 + O(5^150), 1 + 5 + O(5^150), 1 + 5^2 + O(5^150), 1 + 5^3 + O(5^150)] sage: C = Cluster(Matrix(ZZ, 4, 4,[\ [20, 1, 0, 0 ],\ [1, 20, 0, 0 ],\ [0, 0, 20, 1 ],\ [0, 0, 1, 20 ],\ ])) sage: C.roots() Traceback (most recent call last): ... AttributeError: This cluster does not have root information stored.
- set_center(c, check=True)¶
Set the center of
self
toc
, useful to check against examples done by hand.
- size()¶
The size of
self
, the number of roots contained in the cluster.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.size() 3 sage: C = Cluster.from_roots([K(1), K(2), K(5), K(10), K(25)]) sage: C.size() 5 sage: C = Cluster.from_roots([K(1), K(2), K(5), K(10), K(25), K(50)]) sage: C.size() 6 sage: C.children()[2].size() 4
- star()¶
Construct
self*
, ifself
is not a cotwin this is the smallest cluster containingself
whose parent is not übereven (and the top cluster if no such cluster exists). Ifself
is a cotwin, its star is its child of size 2g.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(7,150) sage: x = polygen(K) sage: H = HyperellipticCurve((x^2+7^2)*(x^2-7^(15))*(x-7^6)*(x-7^6-7^9)) sage: R = Cluster.from_curve(H) sage: a = R.children()[2] sage: t1 = a.children()[0] sage: t2 = a.children()[1] sage: t1.star() == a True sage: t2.star() == a True sage: a.star() == a True sage: R.star() == a True
Some cotwins:
sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.star() Cluster with 2 roots and 2 children sage: C = Cluster.from_roots([K(1), K(2), K(10), K(35)]) sage: C.star() Cluster with 2 roots and 2 children sage: C = Cluster.from_roots([K(1), K(5), K(10), K(35)]) sage: C.children()[1].star() Cluster with 2 roots and 2 children
- tamagawa_number(check_semistable=True)¶
Compute the Tamagawa number of
self
.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: x = polygen(K) sage: R = Cluster.from_polynomial((x^4-5^4)*(x+1)*(x+2)) sage: R.tamagawa_number() 2
Example 10.4:
sage: K = Qp(5,150) sage: x = polygen(K) sage: R = Cluster.from_polynomial((x^2-5^2)*(x+1)*(x-1)*(x-2)) sage: R.tamagawa_number() 2
Example 10.6:
sage: p = 7 sage: x = polygen(Qp(p, 200)) sage: w = 2 sage: a = 7 sage: u = 2 sage: z = 3 sage: f = ((x^(2)+1)^(2)-p^(u))*((x-1)^(2)-p^(z))*(x-p^(w / 2))*(x-p^(w / 2+2))*((x^(2)+p^(w+4))^(2)-p^(2*(w+4)+a)) sage: R = Cluster.from_polynomial(f) sage: R.tamagawa_number() == a*(u*z + 2*z*w + u*w) True
Elliptic curve 15.a1:
sage: E = EllipticCurve("15.a1") sage: E.tamagawa_number(3) 2 sage: E = E.short_weierstrass_model(complete_cube=False).change_ring(Qp(3,150)) sage: R = Cluster.from_curve(E) sage: R.tamagawa_number() 2
Elliptic curve 576.c4:
sage: E = EllipticCurve([9, 0]) sage: E.tamagawa_number(3) 2 sage: E = E.short_weierstrass_model(complete_cube=False).change_ring(Qp(3,150)) sage: R = Cluster.from_curve(E) sage: R.is_semistable(Qp(3)) False sage: R.tamagawa_number() Traceback (most recent call last): ... NotImplementedError
Hyperelliptic Curve 630.a.34020.1:
sage: R.<tx> = PolynomialRing(Qp(3,200)) sage: X = HyperellipticCurve(R([60, -24, -91, 2, 41, 12])) sage: C = Cluster.from_curve(X) sage: C.tamagawa_number() 2
Hyperelliptic Curve 4815.a.14445.1:
sage: R.<tx> = PolynomialRing(Qp(3,200)) sage: X = HyperellipticCurve(R([5, 40, 84, 0, -56, -28, -4])) sage: C = Cluster.from_curve(X) sage: C.tamagawa_number() 1
Time limit example:
sage: x = polygen(Qp(7,150)) sage: H = HyperellipticCurve(x^(12) + 36*x^(11) + 534*x^(10) + 4094*x^9 + 17667*x^8 + 44018*x^7 + 61093*x^6 + 44018*x^5 + 17667*x^4 + 4094*x^3 + 534*x^2 + 36*x + 1) sage: C = Cluster.from_curve(H) sage: C.tamagawa_number() 1
- theta(frobenius_reduction=False)¶
A choice of \sqrt{c \prod_{r \notin \mathfrak{s}}\left(z_{\mathfrak{s}}-r\right)}.
If the optional parameter
frobenius_reduction
is set, then the residue of the unit part will be returned.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 5 sage: K = Qp(p,150) sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.theta() Traceback (most recent call last): ... AttributeError: This cluster does not have a leading coefficient stored. sage: x = polygen(K) sage: C = Cluster.from_polynomial((x-1)*(x-(1+p^2))*(x-(1-p^2))*(x-p)*x*(x-p^3)*(x+p^3)) sage: C.theta() 1 + O(5^150) sage: D = C.children()[1] sage: D.theta() 2 + 5 + 2*5^2 + 5^3 + 2*5^4 + 5^5 + 4*5^6 + 2*5^7 + 2*5^8 + 2*5^9 + 5^10 + 4*5^11 + 2*5^13 + 3*5^14 + 4*5^15 + 4*5^16 + 4*5^17 + 5^19 + 4*5^20 + 4*5^22 + 4*5^25 + 5^26 + 3*5^27 + 3*5^30 + 4*5^32 + 3*5^34 + 5^35 + 5^36 + 4*5^37 + 5^38 + 2*5^39 + 3*5^40 + 5^41 + 3*5^42 + 5^43 + 5^44 + 3*5^45 + 2*5^46 + 2*5^48 + 3*5^50 + 2*5^51 + 5^52 + 2*5^53 + 3*5^54 + 4*5^55 + 4*5^56 + 4*5^57 + 5^59 + 2*5^60 + 3*5^61 + 4*5^63 + 2*5^65 + 4*5^66 + 2*5^68 + 3*5^69 + 4*5^70 + 2*5^71 + 4*5^72 + 5^73 + 2*5^74 + 2*5^75 + 3*5^76 + 4*5^77 + 5^78 + 5^79 + 3*5^80 + 4*5^81 + 4*5^82 + 5^83 + 3*5^84 + 4*5^86 + 2*5^87 + 5^88 + 2*5^90 + 5^91 + 3*5^93 + 5^94 + 5^95 + 5^96 + 5^97 + 4*5^99 + 3*5^100 + 5^101 + 3*5^102 + 2*5^103 + 2*5^105 + 5^107 + 5^108 + 4*5^109 + 2*5^110 + 3*5^111 + 4*5^112 + 5^113 + 4*5^114 + 2*5^115 + 4*5^116 + 4*5^117 + 5^118 + 4*5^119 + 2*5^120 + 5^121 + 4*5^122 + 4*5^123 + 5^125 + 3*5^126 + 5^128 + 3*5^131 + 4*5^134 + 3*5^135 + 5^136 + 4*5^137 + 2*5^138 + 5^139 + 3*5^143 + 5^144 + 4*5^145 + 3*5^147 + 5^148 + O(5^150) sage: K = Qp(7,150) sage: x = polygen(K) sage: H = HyperellipticCurve((x^2+7^2)*(x^2-7^(15))*(x-7^6)*(x-7^6-7^9)) sage: R = Cluster.from_curve(H) sage: a = R.children()[0] sage: #a.theta() TODO renable
- theta_squared()¶
c \prod_{r \notin \mathfrak{s}}\left(z_{\mathfrak{s}}-r\right).
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 5 sage: K = Qp(p,150) sage: C = Cluster.from_roots([K(1), K(5), K(10)]) sage: C.theta_squared() Traceback (most recent call last): ... AttributeError: This cluster does not have a leading coefficient stored. sage: x = polygen(K) sage: C = Cluster.from_polynomial((x-1)*(x-(1+p^2))*(x-(1-p^2))*(x-p)*x*(x-p^3)*(x+p^3)) sage: C.theta_squared() 1 + O(5^150) sage: D = C.children()[1] sage: D.theta_squared() == 624 True sage: K = Qp(7,150) sage: x = polygen(K) sage: H = HyperellipticCurve((x^2+7^2)*(x^2-7^(15))*(x-7^6)*(x-7^6-7^9)) sage: R = Cluster.from_curve(H) sage: a = R.children()[0] sage: a.theta_squared() # not tested - TODO renable sage: x = polygen(Qp(3,150)) sage: H = HyperellipticCurve((x-1)*((x-3)^2+81)*((x+3)^2+81)) sage: C = Cluster.from_curve(H) sage: #C.children()[1].children()[0].set_center(3) sage: #C.children()[1].children()[0].theta_squared() == 234 sage: #C.children()[1].children()[1].set_center(-3) sage: #C.children()[1].children()[1].theta_squared() == -468
Example 4.11:
sage: K = Qq(11^3, 200, names="a") sage: a = K.gen() sage: z = K.teichmuller(10*a^2 + 7*a + 8) sage: x = polygen(K) sage: f = prod(x-a for a in [0,1,2,z-11,z+11,z^2 - 11, z^2 +11, z^4 -11, z^4 + 11]).map_coefficients(lambda x: x.trace()/3, new_base_ring=Qp(11, 200)) sage: H = HyperellipticCurve(f) sage: R = Cluster.from_curve(H) sage: t1 = R.children()[3] sage: t2 = R.children()[4] sage: t4 = R.children()[5] sage: z = t1.center() sage: #(t1.theta_squared() - z^2 - 3*z - 7).residue() # also only true with correct order TODO 0 sage: # (t2.theta_squared() + 3*z^2 + 2*z +8).residue() sage: # (t4.theta_squared() + 9*z^2 + z +9).residue()
- top_cluster()¶
Return the top cluster for the picture.
EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: K = Qp(5,150) sage: C = Cluster.from_roots([K(1), K(6), K(26), K(126)]) sage: C.children()[1].children()[1].children()[1].top_cluster().size() 4
- xi(a)¶
Compute \xi_{self}(a) = \max \left\{-\operatorname{ord}_{2}\left(\left[I_{K}: I_{self}\right] a\right), 0\right\}.
EXAMPLES:
Example 12.6
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: p = 5 sage: x = polygen(Qp(p, 150)) sage: R = Cluster.from_polynomial_without_roots(x^5+256) sage: R.xi(R.lambda_tilde()) 3 sage: R.xi(R.depth()) 2
Example 12.7
sage: from sage_cluster_pictures.cluster_pictures import Cluster sage: x = polygen(Qp(7)) sage: R = Cluster.from_polynomial(x^5+5*x^4+40*x^3+80*x^2+256*x) sage: R.xi(R.lambda_tilde()) 0 sage: R.xi(R.depth()) 0 sage: s = R.children()[1] sage: R.xi(s.lambda_tilde()) 1 sage: R.xi(s.depth()) 2
- sage_cluster_pictures.cluster_pictures.orbit_decomposition(F, S, cond=None)¶
Decompose a list
S
into orbits under the functionF
, returning only those satisfyingcond
.EXAMPLES:
sage: from sage_cluster_pictures.cluster_pictures import orbit_decomposition sage: orbit_decomposition(lambda x: x + 1, list(Integers(15))) [[14, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13]] sage: orbit_decomposition(lambda x: x + 1, list(Integers(15)), cond = lambda x: len(x) < 1) []