-
Notifications
You must be signed in to change notification settings - Fork 126
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Strict transform of an ideal in Cox ring #4154
base: master
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -44,3 +44,119 @@ end | |
function total_transform(f::AbsBlowupMorphism, II::AbsIdealSheaf) | ||
return pullback(f, II) | ||
end | ||
|
||
@doc raw""" | ||
_minimal_supercone(X::NormalToricVariety, r::AbstractVector{<:IntegerUnion}) | ||
|
||
Given a ray $r$ inside the support of the simplicial fan $Σ$ of a normal toric variety~$X$, not coinciding with any ray in $Σ(1)$, return the unique cone $σ$ in $Σ$ such that $r$ is in the relative interior of $σ$. | ||
|
||
# Examples | ||
```jldoctest | ||
julia> X = projective_space(NormalToricVariety, 3) | ||
Normal toric variety | ||
|
||
julia> r = [1, 1, 0] | ||
2-element Vector{Int64}: | ||
1 | ||
1 | ||
|
||
julia> Oscar._minimal_supercone(X, r) | ||
Polyhedral cone in ambient dimension 3 | ||
|
||
julia> rays(c) | ||
2-element SubObjectIterator{RayVector{QQFieldElem}}: | ||
[1, 0, 0] | ||
[0, 1, 0] | ||
``` | ||
""" | ||
function _minimal_supercone(X::NormalToricVariety, r::AbstractVector{<:Union{IntegerUnion, QQFieldElem}}) | ||
@assert is_orbifold(X) "Only implemented when fan is simplicial" | ||
contained_in_support_of_fan = false | ||
mcone = maximal_cones(X)[1] # initialize `mcone`, fixing its type | ||
|
||
mcones = maximal_cones(X) | ||
while true | ||
contained_in_subcone = false | ||
for c in mcones | ||
if r in c | ||
contained_in_support_of_fan = true | ||
contained_in_subcone = true | ||
mcone = c | ||
end | ||
end | ||
@assert contained_in_support_of_fan "Ray not contained in the support of the fan" | ||
!contained_in_subcone && return mcone | ||
n_rays(mcone) == 1 && return mcone | ||
|
||
# set mcones to be the facets of mcone | ||
mcones = [cone(setdiff(collect(rays(mcone)), [ray])) for ray in rays(mcone)] | ||
end | ||
end | ||
|
||
function _cox_ring_homomorphism(f::ToricBlowupMorphism) | ||
@assert is_normal(codomain(f)) | ||
@assert is_orbifold(codomain(f)) "Only implemented when fan is simplicial" | ||
Y = domain(f) | ||
@assert !has_torusfactor(codomain(f)) "Only implemented when there are no torus factors" | ||
@assert n_rays(Y) == n_rays(codomain(f)) + 1 "Only implemented when the blowup adds a ray" | ||
@assert grading_group(cox_ring(Y)) === class_group(Y) | ||
G = class_group(Y) | ||
n = number_of_generators(G) | ||
new_ray = rays(domain(f))[index_of_new_ray(f)] | ||
c = Oscar._minimal_supercone(Y, new_ray) | ||
U = affine_normal_toric_variety(c) | ||
d = order(class_group(U)) | ||
# TODO: finish this... | ||
|
||
|
||
new_var = cox_ring(Y)[index_of_new_ray(f)] | ||
M = generator_degrees(cox_ring(Y)) | ||
@assert M[index_of_new_ray(f)][n] < 0 "Assuming the blowup adds a new column vector to `Oscar.generator_degrees(cox_ring(codomain(f)))`, the entry of that vector corresponding to the new ray should be negative. If not, multiply by -1." | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Your error messages in case of failing asserts seem pretty long to me. Please try to make them shorter and maybe add appropriate notes to the documentation instead. |
||
ind = Int64(abs(M[index_of_new_ray(f)][n])) | ||
for i in 1:n_rays(Y) | ||
i == index_of_new_ray(f) || @assert M[i][n] >= 0 "Assuming the blowup adds a new column vector to `Oscar.generator_degrees(cox_ring(codomain(f)))` for which the entry corresponding to the new ray is negative, the entries corresponding to all the other rays should be nonnegative. If not, add integer multiples of the other columns until it is." | ||
Comment on lines
+116
to
+117
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Do you want to say |
||
end | ||
if ind == 1 | ||
S = cox_ring(Y) | ||
inj = hom(S, S, gens(S)) | ||
elseif ind > 1 | ||
# Change grading so that the negative entry would be -1 | ||
xs = ZZRingElem[] | ||
for i in 1:n-1 | ||
push!(xs, M[index_of_new_ray(f)][i]) | ||
end | ||
push!(xs, ZZRingElem(-1)) | ||
M_new = deepcopy(M) | ||
M_new[index_of_new_ray(f)] = G(xs) | ||
S_ungraded = forget_grading(cox_ring(Y)) | ||
S = grade(S_ungraded, M_new)[1] | ||
inj = hom(cox_ring(Y), S, gens(S)) | ||
end | ||
F = hom(cox_ring(codomain(f)), S, [inj(new_var^(M[i][n])*S[i]) for i in 1:n_rays(Y) if i != index_of_new_ray(f)]) | ||
return (F, ind) | ||
end | ||
|
||
function strict_transform(f::ToricBlowupMorphism, I::MPolyIdeal) | ||
F, ind = _cox_ring_homomorphism(f) | ||
Y = domain(f) | ||
Comment on lines
+139
to
+141
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Thanks for looking into this! This is to compute the strict transform of an ideal in the cox ring of the codomain, correct? I would probably insert an Once this is done, I would be curious to compare performance with the chart-based approach! |
||
S = cox_ring(Y) | ||
new_var = S[index_of_new_ray(f)] | ||
J = saturation(F(I), ideal(new_var)) | ||
if ind == 1 | ||
return J | ||
elseif ind > 1 | ||
xs = elem_type(S)[] | ||
for gen in gens(J) | ||
new_exponent_vectors = Vector{Int64}[] | ||
for i in 1:length(terms(gen)) | ||
exp_vec = exponent_vector(gen, i) | ||
bool, result = divides(exp_vec[index_of_new_ray(f)], ind) | ||
@assert bool "Given the finite set of generators of `J`, the exponent of `new_var` in every monomial of every member should be divisible by `ind`. If not, first make sure that none of the generators of `J` is divisible by `new_var`." | ||
exp_vec[index_of_new_ray(f)] = result | ||
push!(new_exponent_vectors, exp_vec) | ||
end | ||
push!(xs, S(collect(coefficients(gen)), new_exponent_vectors)) | ||
end | ||
return ideal(cox_ring(Y), xs) | ||
end | ||
end |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
First define G as the class_group(Y) and then use G in the assert, since you need G afterwards anyway and in the case of failure of the assert, you did not loose anything.