Resolutions
Functions for creating free resolutions of modules and ideals in Singular.jl return a special Singular object of type sresolution{T}
. The support in Singular.jl for this type primarily exists to allow interaction with such resolutions. Free resolutions can have the property of being minimal, which is specified by the minimal
field of the sresolution{T}
type.
Resolution objects have a parent object which represents the set of resolutions they belong to, the data for which is given by the polynomial ring $R$ over which the modules in the resolution are defined.
The types of resolutions and associated parent objects are given in the following table according to the library providing them.
Library | Element type | Parent type |
---|---|---|
Singular | sresolution{T} | Singular.ResolutionSet{T} |
These types are parameterised by the type of elements in the polynomial ring $R$ over which the modules belonging to the resolution are defined.
All resolution types belong directly to the abstract type SetElem
and all the resolution set parent object types belong to the abstract type Set
.
Resolution functionality
Singular.jl resolutions implement standard operations one would expect on all AbstractAlgebra compatible objects. These include:
- Operations common to all AbstractAlgebra objects, such as
parent
,base_ring
,elem_type
,parent_type
,parent
,deepcopy
, etc.
Below, we describe all of the functionality for Singular.jl resolutions that is not included in this list of basic operations.
Constructors
There are currently two ways to create resolutions in Singular.jl: They can either be created by taking the free resolution of an ideal or module over a polynomial ring, as described in the relevant sections of the documentation, or they can be created by the following constructor:
Singular.Resolution
— MethodResolution(C::Vector{smodule{T}}) where T <: AbstractAlgebra.RingElem
Create a new resolution whose maps are given by the elements of an array C of modules. Note that it is not checked that the maps are actually composable and that their pairwise composition is the zero map, that is, that the created resolution is a complex.
Example
julia> R, (x, y) = polynomial_ring(QQ, ["x", "y"])
(Singular Polynomial Ring (QQ),(x,y),(dp(2),C), spoly{n_Q}[x, y])
julia> M1 = Singular.Module(R, vector(R, x), vector(R, y))
Singular Module over Singular Polynomial Ring (QQ),(x,y),(dp(2),C), with Generators:
x*gen(1)
y*gen(1)
julia> M2 = Singular.Module(R, vector(R, y, -x))
Singular Module over Singular Polynomial Ring (QQ),(x,y),(dp(2),C), with Generators:
-x*gen(2)+y*gen(1)
julia> F = Resolution([M1, M2]);
julia> F[1]
Singular Module over Singular Polynomial Ring (QQ),(x,y),(dp(2),C), with Generators:
x*gen(1)
y*gen(1)
julia> F[2]
Singular Module over Singular Polynomial Ring (QQ),(x,y),(dp(2),C), with Generators:
-x*gen(2)+y*gen(1)
Alternatively, resolutions can be refined to minimal resolutions, as described below.
Other than this, there are currently no additional ways to create resolutions in Singular.jl.
Basic manipulation
Base.length
— Methodlength(r::sresolution)
Return the length of the resolution. This is what is mathematically meant by the length of a resolution. Over a field, this should be at most the number of variables in the polynomial ring.
Singular.jl overloads the getindex
function so that one can access the modules in a resolution $F$.
F[n::Int]
Examples
julia> R, (w, x, y, z) = polynomial_ring(QQ, ["w", "x", "y", "z"])
(Singular polynomial ring (QQ),(w,x,y,z),(dp(4),C), spoly{n_Q}[w, x, y, z])
julia> I = Ideal(R, w^2 - x*z, w*x - y*z, x^2 - w*y, x*y - z^2, y^2 - w*z)
Singular ideal over Singular polynomial ring (QQ),(w,x,y,z),(dp(4),C) with generators (w^2 - x*z, w*x - y*z, x^2 - w*y, x*y - z^2, y^2 - w*z)
julia> F = fres(std(I), 0)
Singular resolution: R^1 <- R^5 <- R^6 <- R^2
julia> n = length(F)
3
julia> M1 = F[1]
Singular ideal over Singular polynomial ring (QQ),(w,x,y,z),(dp(4),C) with generators (y^2 - w*z, x*y - z^2, x^2 - w*y, w*x - y*z, w^2 - x*z)
Betti numbers
Singular.betti
— Methodbetti(r::sresolution)
Return the Betti numbers, i.e. the ranks of the free modules in the given free resolution. These are returned as a Julia array of Int
s. Note that the output of this command is useful only in the graded case.
Examples
julia> R, (w, x, y, z) = polynomial_ring(QQ, ["w", "x", "y", "z"])
(Singular polynomial ring (QQ),(w,x,y,z),(dp(4),C), spoly{n_Q}[w, x, y, z])
julia> I = Ideal(R, w^2 - x*z, w*x - y*z, x^2 - w*y, x*y - z^2, y^2 - w*z)
Singular ideal over Singular polynomial ring (QQ),(w,x,y,z),(dp(4),C) with generators (w^2 - x*z, w*x - y*z, x^2 - w*y, x*y - z^2, y^2 - w*z)
julia> F = fres(std(I), 3)
Singular resolution: R^1 <- R^5 <- R^6 <- R^2
julia> M = minres(F)
Singular resolution: R^1 <- R^5 <- R^5 <- R^1
julia> B = betti(M)
3×4 Matrix{Int32}:
1 0 0 0
0 5 5 0
0 0 0 1
Minimal resolutions
Singular.minres
— Methodminres{T <: Nemo.FieldElem}(r::sresolution{spoly{T}})
Return a minimal free resolution, given any free resolution. In the graded case, there exists a uniquely determined minimal resolution. If the supplied resolution is already minimal, it may be returned without making a copy.
Examples
julia> R, (w, x, y, z) = polynomial_ring(QQ, ["w", "x", "y", "z"])
(Singular polynomial ring (QQ),(w,x,y,z),(dp(4),C), spoly{n_Q}[w, x, y, z])
julia> I = Ideal(R, w^2 - x*z, w*x - y*z, x^2 - w*y, x*y - z^2, y^2 - w*z)
Singular ideal over Singular polynomial ring (QQ),(w,x,y,z),(dp(4),C) with generators (w^2 - x*z, w*x - y*z, x^2 - w*y, x*y - z^2, y^2 - w*z)
julia> F = fres(std(I), 3)
Singular resolution: R^1 <- R^5 <- R^6 <- R^2
julia> M = minres(F)
Singular resolution: R^1 <- R^5 <- R^5 <- R^1