Revision 3a654fb6556f8b24081daeae9249680d8ff68214 authored by Sebastian Gutsche on 06 October 2016, 15:26:25 UTC, committed by Sebastian Gutsche on 06 October 2016, 15:26:25 UTC
1 parent 8ba25ff
GrothendieckGroup.gi
#############################################################################
##
## GrothendieckGroup.gi Modules package
##
## Copyright 2011, Mohamed Barakat, University of Kaiserslautern
##
## Implementations for elements of the Grothendieck group of a projective space.
##
#############################################################################
####################################
#
# representations:
#
####################################
## <#GAPDoc Label="IsElementOfGrothendieckGroupOfProjectiveSpaceRep">
## <ManSection>
## <Filt Type="Representation" Arg="P" Name="IsElementOfGrothendieckGroupOfProjectiveSpaceRep"/>
## <Returns><C>true</C> or <C>false</C></Returns>
## <Description>
## The representation of elements of the Grothendieck group of a projective space.
## <Listing Type="Code"><![CDATA[
DeclareRepresentation( "IsElementOfGrothendieckGroupOfProjectiveSpaceRep",
IsElementOfGrothendieckGroupOfProjectiveSpace,
[ ] );
## ]]></Listing>
## </Description>
## </ManSection>
## <#/GAPDoc>
##
## <#GAPDoc Label="IsPolynomialModuloSomePowerRep">
## <ManSection>
## <Filt Type="Representation" Arg="c" Name="IsPolynomialModuloSomePowerRep"/>
## <Returns><C>true</C> or <C>false</C></Returns>
## <Description>
## The representation of polynomials modulo some power.
## <Listing Type="Code"><![CDATA[
DeclareRepresentation( "IsPolynomialModuloSomePowerRep",
IsPolynomialModuloSomePower,
[ "polynomial", "indeterminate", "normalize" ] );
## ]]></Listing>
## </Description>
## </ManSection>
## <#/GAPDoc>
##
## <#GAPDoc Label="IsChernPolynomialWithRankRep">
## <ManSection>
## <Filt Type="Representation" Arg="c" Name="IsChernPolynomialWithRankRep"/>
## <Returns><C>true</C> or <C>false</C></Returns>
## <Description>
## The representation of Chern polynomials with rank.
## <Listing Type="Code"><![CDATA[
DeclareRepresentation( "IsChernPolynomialWithRankRep",
IsChernPolynomialWithRank,
[ "indeterminate", "normalize" ] );
## ]]></Listing>
## </Description>
## </ManSection>
## <#/GAPDoc>
##
## <#GAPDoc Label="IsChernCharacterRep">
## <ManSection>
## <Filt Type="Representation" Arg="c" Name="IsChernCharacterRep"/>
## <Returns><C>true</C> or <C>false</C></Returns>
## <Description>
## The representation of Chern character.
## <Listing Type="Code"><![CDATA[
DeclareRepresentation( "IsChernCharacterRep",
IsChernCharacter,
[ "indeterminate", "normalize" ] );
## ]]></Listing>
## </Description>
## </ManSection>
## <#/GAPDoc>
##
####################################
#
# families and types:
#
####################################
# a new family:
BindGlobal( "TheFamilyOfCombinatorialPolynomials",
NewFamily( "TheFamilyOfCombinatorialPolynomials" ) );
# new types:
BindGlobal( "TheTypeElementOfGrothendieckGroupOfProjectiveSpace",
NewType( TheFamilyOfCombinatorialPolynomials,
IsElementOfGrothendieckGroupOfProjectiveSpaceRep ) );
BindGlobal( "TheTypePolynomialModuloSomePower",
NewType( TheFamilyOfCombinatorialPolynomials,
IsPolynomialModuloSomePowerRep ) );
BindGlobal( "TheTypeChernPolynomialWithRank",
NewType( TheFamilyOfCombinatorialPolynomials,
IsChernPolynomialWithRankRep ) );
BindGlobal( "TheTypeChernCharacter",
NewType( TheFamilyOfCombinatorialPolynomials,
IsChernCharacterRep ) );
####################################
#
# methods for properties:
#
####################################
##
InstallMethod( IsIntegral,
"for an element of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep ],
function( P )
return ForAll( Coefficients( P ), IsInt );
end );
##
InstallMethod( IsNumerical,
"for a univariate polynomial and an integer",
[ IsUnivariatePolynomial ],
function( chi )
local P;
if IsZero( chi ) then
return true;
fi;
## being numerical or not does not depend on the ambient dimension
P := CreateElementOfGrothendieckGroupOfProjectiveSpace( chi, Degree( chi ) );
return IsIntegral( P );
end );
##
InstallMethod( IsIntegral,
"for a Chern characters",
[ IsChernCharacterRep ],
function( ch )
local chi;
chi := HilbertPolynomial( ch );
return IsNumerical( chi );
end );
##
InstallMethod( IsIntegral,
"for a Chern polynomial with rank",
[ IsChernPolynomialWithRankRep ],
function( c )
local ch;
ch := ChernCharacter( c );
return IsIntegral( ch );
end );
####################################
#
# methods for attributes:
#
####################################
##
InstallMethod( ChernPolynomial,
"for a univariate polynomial, an integer, and a ring element",
[ IsUnivariatePolynomial, IsInt, IsRingElement ],
function( chi, dim, h )
local P;
P := CreateElementOfGrothendieckGroupOfProjectiveSpace( chi, dim );
return ChernPolynomial( P );
end );
##
InstallMethod( ChernPolynomial,
"for a univariate polynomial and an integer",
[ IsUnivariatePolynomial, IsInt ],
function( chi, dim )
local h;
h := VariableForChernPolynomial( );
return ChernPolynomial( chi, dim, h );
end );
##
InstallMethod( ZERO,
"for an element of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep and AssociatedPolynomial ],
function( P )
local chi, K_0;
chi := AssociatedPolynomial( P );
K_0 := GrothendieckGroup( P );
return CreateElementOfGrothendieckGroupOfProjectiveSpace( 0 * chi, K_0 );
end );
##
InstallMethod( Dimension,
"for an element of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep ],
function( P )
local coeffs, l, h;
coeffs := Coefficients( P );
coeffs := Reversed( coeffs );
l := Length( coeffs );
h := PositionNonZero( coeffs );
return l - h;
end );
##
InstallMethod( Dimension,
"for an element of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep and HasAssociatedPolynomial ],
function( P )
return Degree( AssociatedPolynomial( P ) );
end );
##
InstallMethod( Dimension,
"for an element of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep and IsZero ],
function( P )
return -1;
end );
##
InstallMethod( DegreeOfElementOfGrothendieckGroupOfProjectiveSpace,
"for an element of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep ],
function( P )
local coeffs, l, h;
coeffs := Coefficients( P );
coeffs := Reversed( coeffs );
l := Length( coeffs );
h := PositionNonZero( coeffs );
return coeffs[h];
end );
##
InstallMethod( DegreeOfElementOfGrothendieckGroupOfProjectiveSpace,
"for an element of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep and HasAssociatedPolynomial ],
function( P )
local h;
h := AssociatedPolynomial( P );
return LeadingCoefficient( h ) * Factorial( Degree( h ) );
end );
##
InstallMethod( DegreeOfElementOfGrothendieckGroupOfProjectiveSpace,
"for an element of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep and IsZero ],
function( P )
return 0;
end );
##
InstallMethod( Degree,
"for an element of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep ],
DegreeOfElementOfGrothendieckGroupOfProjectiveSpace );
##
InstallMethod( CoefficientsOfElementOfGrothendieckGroupOfProjectiveSpace,
"for a univariate polynomial",
[ IsUnivariatePolynomial ],
function( h )
local dim, deg, C, s;
if IsZero( h ) then
return [ ];
fi;
dim := Degree( h );
deg := LeadingCoefficient( h ) * Factorial( dim );
C := ListWithIdenticalEntries( dim + 1, 0 );
C[dim + 1] := deg;
s := IndeterminateOfUnivariateRationalFunction( h );
h := h - deg * _Binomial( s + dim, dim );
while not IsZero ( h ) do
dim := Degree( h );
deg := LeadingCoefficient( h ) * Factorial( dim );
C[dim + 1] := deg;
h := h - deg * _Binomial( s + dim, dim );
od;
return C;
end );
##
InstallMethod( AdditiveInverse,
"for an element of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep ],
function( P )
local negP;
negP := -UnderlyingModuleElement( P );
negP := CreateElementOfGrothendieckGroupOfProjectiveSpace( -negP );
if IsBound( P!.DisplayTwistedCoefficients ) and P!.DisplayTwistedCoefficients = true then
negP!.DisplayTwistedCoefficients := true;
fi;
return negP;
end );
##
InstallMethod( AdditiveInverse,
"for an element of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep and HasAssociatedPolynomial ],
function( P )
local chi, K_0, negP;
chi := AssociatedPolynomial( P );
K_0 := GrothendieckGroup( P );
negP := CreateElementOfGrothendieckGroupOfProjectiveSpace( -chi, K_0 );
if IsBound( P!.DisplayTwistedCoefficients ) and P!.DisplayTwistedCoefficients = true then
negP!.DisplayTwistedCoefficients := true;
fi;
return negP;
end );
##
InstallMethod( ChernPolynomial,
"for an element of the Grothendieck group of a projective space and a ring element",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep, IsRingElement ],
function( P, h )
local dim, c, coeffs, C, C_O_i;
Assert( 0, IsIntegral( P ) );
dim := AmbientDimension( P );
coeffs := Coefficients( P, "twisted" );
c := 1 * h^0;
## it is ugly that we need this
SetIndeterminateOfUnivariateRationalFunction( c, h );
## checking this property sets it
Assert( 0, IsUnivariatePolynomial( c ) );
C := CreateChernPolynomial( 0, c, dim );
if IsZero( P ) then
return C;
fi;
## we could have used CreateChernPolynomial( 0, 1 - i * h, dim ) and
## defined C := CreateChernPolynomial( Rank( C ), c, dim ) above,
## but this is conceptually more appealing; see the assertion below
C_O_i := List( [ 0 .. dim ], i -> CreateChernPolynomial( 1, 1 - i * h, dim ) );
C := C * Product( [ 0 .. dim ], i -> C_O_i[i + 1]^coeffs[i + 1] );
## we know the rank a priori
Assert( 0, Rank( C ) = Sum( coeffs ) );
SetElementOfGrothendieckGroupOfProjectiveSpace( C, P );
return C;
end );
##
InstallMethod( ChernPolynomial,
"for an element of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep ],
function( P )
local h;
h := VariableForChernPolynomial( );
return ChernPolynomial( P, h );
end );
##
InstallMethod( OneMutable,
"for a polynomial modulo some power",
[ IsPolynomialModuloSomePowerRep ],
function( p )
local o;
o := 1 + 0 * p!.indeterminate;
## checking this property sets it
Assert( 0, IsUnivariatePolynomial( o ) );
return CreatePolynomialModuloSomePower( o, AmbientDimension( p ) );
end );
##
InstallMethod( OneMutable,
"for a Chern polynomial with rank",
[ IsChernPolynomialWithRankRep ],
function( C )
local O;
O := One( TotalChernClass( C ) );
return CreateChernPolynomial( 0, O );
end );
##
InstallMethod( Dual,
"for a Chern polynomial with rank",
[ IsChernPolynomialWithRankRep ],
function( C )
local h, dual;
h := VariableForChernPolynomial( );
dual := Value( C, -h );
SetDual( dual, C );
return dual;
end );
##
InstallMethod( ChernCharacter,
"for a Chern polynomial with rank",
[ IsChernPolynomialWithRankRep ],
function( c )
local C, indets, dim, u, ch;
C := Coefficients( c );
indets := List( [ 1 .. Length( C ) ], i -> Indeterminate( Rationals, i ) );
dim := AmbientDimension( c );
u := VariableForChernCharacter( );
ch := Sum( [ 1 .. dim ],
i -> ExpressSymmetricPolynomialInElementarySymmetricPolynomials(
Sum( indets, x -> x^i ), indets, C ) * u^i / Factorial( i ) );
ch := Rank( c ) + ch + 0 * u;
## checking this property sets it
Assert( 0, IsUnivariatePolynomial( ch ) );
return CreateChernCharacter( ch, dim );
end );
##
InstallMethod( HilbertPolynomial,
"for a Chern polynomial with rank",
[ IsChernPolynomialWithRankRep ],
function( c )
return HilbertPolynomial( ChernCharacter( c ) );
end );
##
InstallMethod( HilbertPolynomial,
"for a Chern character",
[ IsChernCharacterRep ],
function( ch )
local dim, u, t, chi, normalize, exp, todd;
dim := AmbientDimension( ch );
u := ch!.indeterminate;
t := VariableForHilbertPolynomial( );
chi := 0 * t;
## it is ugly that we need this
SetIndeterminateOfUnivariateRationalFunction( chi, t );
## checking this property sets it
Assert( 0, IsUnivariatePolynomial( chi ) );
if IsZero( ch ) then
return chi;
fi;
normalize := function( poly )
return PolynomialReduction( poly, [ u^(dim + 1) ], MonomialLexOrdering( ) )[1];
end;
exp := Sum( [ 0 .. dim ], i -> ( t * u )^i / Factorial( i ) );
todd := Sum( [ 0 .. dim ], i -> (-1)^i * u^i / Factorial( i + 1 ) );
todd := CreatePolynomialModuloSomePower( todd, dim );
todd := todd^-(dim + 1);
todd := todd!.polynomial;
ch := ChernCharacterPolynomial( ch );
ch := ch!.polynomial;
## Hirzebruch-Riemann-Roch
ch := normalize( normalize( exp * ch ) * todd );
if DegreeIndeterminate( ch, u ) < dim then
return chi;
fi;
chi := PolynomialCoefficientsOfPolynomial( ch, u )[dim + 1];
## it is ugly that we need this
SetIndeterminateOfUnivariateRationalFunction( chi, t );
## checking this property sets it
Assert( 0, IsUnivariatePolynomial( chi ) );
return chi;
end );
##
InstallMethod( RankOfObject,
"for grothendieck group elements of projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep ],
function( element )
local module_element;
module_element := UnderlyingModuleElement( element );
module_element := UnderlyingListOfRingElementsInCurrentPresentation( module_element );
return module_element[ Length( module_element ) ];
end );
##
InstallMethod( ChernPolynomial,
"for a Chern character",
[ IsChernCharacterRep ],
function( ch )
local HP, d;
HP := HilbertPolynomial( ch );
d := AmbientDimension( ch );
return ChernPolynomial( CreateElementOfGrothendieckGroupOfProjectiveSpace( HP, d ) );
end );
##
InstallMethod( DegreeOfChernPolynomial,
"for a chern polynomial with rank",
[ IsChernPolynomialWithRankRep ],
function( c )
return Degree( TotalChernClass( c )!.polynomial );
end );
####################################
#
# methods for operations:
#
####################################
##
InstallGlobalFunction( VariableForChernPolynomial,
function( arg )
local h;
if not IsBound( HOMALG_MODULES.variable_for_Chern_polynomial ) then
if Length( arg ) > 0 and IsString( arg[1] ) then
h := arg[1];
else
h := "h";
fi;
h := Indeterminate( Rationals, h );
HOMALG_MODULES.variable_for_Chern_polynomial := h;
fi;
return HOMALG_MODULES.variable_for_Chern_polynomial;
end );
##
InstallGlobalFunction( VariableForChernCharacter,
function( arg )
local u;
if not IsBound( HOMALG_MODULES.variable_for_Chern_character ) then
if Length( arg ) > 0 and IsString( arg[1] ) then
u := arg[1];
else
u := "u";
fi;
u := Indeterminate( Rationals, u );
HOMALG_MODULES.variable_for_Chern_character := u;
fi;
return HOMALG_MODULES.variable_for_Chern_character;
end );
##
InstallMethod( ElementarySymmetricPolynomial,
"for an integer and a list (of indeterminates/ring elemets)",
[ IsInt, IsList ],
function( deg, indets )
local l, zero, sym;
l := Length( indets );
if l = 0 then
Error( "the list of indeterminates (resp. ring elements) is empty\n" );
fi;
zero := 0 * Sum( indets );
IsPolynomial( zero );
if deg = 0 then
return zero + 1;
elif deg < 0 or deg > l then
return zero;
fi;
sym := Combinations( indets, deg );
sym := Sum( List( sym, Product ) );
IsPolynomial( sym );
return sym;
end );
##
InstallGlobalFunction( ExpressSymmetricPolynomialInElementarySymmetricPolynomials,
function( poly, indets, elmsym )
local symm, one, elementary_symmetric_polynomials,
elementary_symmetric_polynomial, transposed_exponents, expo, l, coeff;
if Length( indets ) <> Length( elmsym ) then
Error( "the number of indeterminates and the number of placeholders",
"of elementary symmetric polynomials must coincide\n" );
fi;
symm := 0 * Sum( indets );
IsPolynomial( symm );
if IsZero( poly ) then
return symm;
fi;
one := Sum( indets )^0;
IsPolynomial( one );
## list to cache the elementary symmetric polynomials
elementary_symmetric_polynomials := [ ];
elementary_symmetric_polynomial := function( c, i )
if c = 0 then
return one;
fi;
if not IsBound( elementary_symmetric_polynomials[i + 1] ) then
elementary_symmetric_polynomials[i + 1] :=
ElementarySymmetricPolynomial( i, indets );
fi;
return elementary_symmetric_polynomials[i + 1];
end;
transposed_exponents := function( expo )
local l, i, j;
expo := Filtered( expo, i -> i <> 0 );
Sort( expo );
l := Length( expo );
for i in [ 1 .. l ] do
for j in [ i + 1 .. l ] do
expo[j] := expo[j] - expo[i];
od;
od;
return Reversed( expo );
end;
expo := LeadingMonomial( poly );
expo := expo{List( [ 1 .. Length( expo ) / 2 ], i -> 2 * i )};
expo := transposed_exponents( expo );
l := Length( expo );
while not IsZero( poly ) do
coeff := LeadingCoefficient( poly );
poly := poly - coeff * Product( [ 1 .. l ],
i -> elementary_symmetric_polynomial( expo[i], i )^expo[i] );
symm := symm + coeff * Product( [ 1 .. l ],
i -> elmsym[i]^expo[i] );
expo := LeadingMonomial( poly );
expo := expo{List( [ 1 .. Length( expo ) / 2 ], i -> 2 * i )};
expo := transposed_exponents( expo );
l := Length( expo );
od;
return symm;
end );
##
InstallMethod( Coefficients,
"for an element of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep ],
function( P )
P := UnderlyingModuleElement( P );
P := UnderlyingMorphism( P );
P := MatrixOfMap( P, 1, 1 );
P := Eval( P );
return P!.matrix[1];
end );
##
InstallMethod( Coefficients,
"for an element of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep, IsString ],
function( P, twisted )
local dim, coeffs;
if IsBound( P!.TwistedCoefficients ) then
return P!.TwistedCoefficients;
fi;
dim := AmbientDimension( P );
coeffs := Coefficients( P );
coeffs := List( [ 0 .. dim ], i -> Sum( [ 0 .. dim ], d -> (-1)^i * _Binomial( dim - d, i ) * coeffs[d + 1] ) );
P!.TwistedCoefficients := coeffs;
return coeffs;
end );
##
InstallMethod( \+,
"for two elements of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep,
IsElementOfGrothendieckGroupOfProjectiveSpaceRep ],
function( P1, P2 )
local P;
if not IsIdenticalObj( GrothendieckGroup( P1 ), GrothendieckGroup( P2 ) ) then
Error( "the Grothendieck groups of the two elements are not identical\n" );
fi;
P := UnderlyingModuleElement( P1 ) + UnderlyingModuleElement( P2 );
P := CreateElementOfGrothendieckGroupOfProjectiveSpace( P );
if IsBound( P1!.DisplayTwistedCoefficients ) and P1!.DisplayTwistedCoefficients = true and
IsBound( P2!.DisplayTwistedCoefficients ) and P2!.DisplayTwistedCoefficients = true then
P!.DisplayTwistedCoefficients := true;
fi;
return P;
end );
##
InstallMethod( \+,
"for two elements of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep and HasAssociatedPolynomial,
IsElementOfGrothendieckGroupOfProjectiveSpaceRep and HasAssociatedPolynomial ],
function( P1, P2 )
local K_0, chi, P;
K_0 := GrothendieckGroup( P1 );
if not IsIdenticalObj( K_0, GrothendieckGroup( P2 ) ) then
Error( "the Grothendieck groups of the two elements are not identical\n" );
fi;
chi := AssociatedPolynomial( P1 ) + AssociatedPolynomial( P2 );
P := CreateElementOfGrothendieckGroupOfProjectiveSpace( chi, K_0 );
if IsBound( P1!.DisplayTwistedCoefficients ) and P1!.DisplayTwistedCoefficients = true and
IsBound( P2!.DisplayTwistedCoefficients ) and P2!.DisplayTwistedCoefficients = true then
P!.DisplayTwistedCoefficients := true;
fi;
return P;
end );
##
InstallMethod( Value,
"for an element of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep, IsRat ],
function( P, x )
return Value( AssociatedPolynomial( P ), x );
end );
##
InstallMethod( Value,
"for an element of the Grothendieck group of a projective space",
[ IsPolynomialModuloSomePowerRep, IsRingElement ],
function( poly, x )
local dim;
dim := AmbientDimension( poly );
poly := Value( poly!.polynomial, x );
return CreatePolynomialModuloSomePower( poly, dim );
end );
##
InstallMethod( Rank,
"for a Chern polynomial with rank",
[ IsChernPolynomialWithRankRep ],
RankOfObject );
##
InstallMethod( Value,
"for an element of the Grothendieck group of a projective space",
[ IsChernPolynomialWithRankRep, IsRingElement ],
function( c, x )
local r, poly;
r := Rank( c );
poly := Value( TotalChernClass( c ), x );
return CreateChernPolynomial( r, poly );
end );
##
InstallMethod( \*,
"for two polynomials modulo some power",
[ IsPolynomialModuloSomePowerRep, IsPolynomialModuloSomePowerRep ],
function( poly1, poly2 )
local dim, p1, p2, p;
dim := AmbientDimension( poly1 );
if dim <> AmbientDimension( poly2 ) then
Error( "polynomials are defined modulo different powers\n" );
fi;
if poly1!.indeterminate <> poly2!.indeterminate then
Error( "indeterminates of polynomials differ\n" );
fi;
p1 := poly1!.polynomial;
p2 := poly2!.polynomial;
p := poly1!.normalize( p1 * p2 );
## checking this property sets it
Assert( 0, IsUnivariatePolynomial( p ) );
return CreatePolynomialModuloSomePower( p, dim );
end );
##
InstallMethod( \*,
"for two Chern polynomials with rank",
[ IsChernPolynomialWithRankRep, IsChernPolynomialWithRankRep ],
function( C1, C2 )
local r, c;
r := Rank( C1 ) + Rank( C2 );
c := TotalChernClass( C1 ) * TotalChernClass( C2 );
return CreateChernPolynomial( r, c );
end );
##
InstallMethod( InverseOp,
"for a polynomial modulo some power",
[ IsPolynomialModuloSomePowerRep ],
function( poly )
local dim, h, normalize, const, y, p, p_i, ldeg, i;
dim := AmbientDimension( poly );
h := poly!.indeterminate;
normalize := poly!.normalize;
poly := poly!.polynomial;
if IsZero( poly ) then
Error( "division by the zero polynomial\n" );
fi;
const := CoefficientsOfUnivariatePolynomial( poly )[1];
if IsZero( const ) then
Error( "the polynomial is not invertible\n" );
fi;
poly := poly / const;
## y might be zero
y := 1 - poly;
p := y^0; ## retain the type of y
## it is ugly that we need this
SetIndeterminateOfUnivariateRationalFunction( p, h );
p_i := p;
if IsZero( y ) then
p := p / const;
## it is ugly that we need this
SetIndeterminateOfUnivariateRationalFunction( p, h );
## checking this property sets it
Assert( 0, IsUnivariatePolynomial( p ) );
return CreatePolynomialModuloSomePower( p, dim );
fi;
ldeg := PositionNonZero( CoefficientsOfUnivariatePolynomial( y ) ) - 1;
for i in [ 1 .. dim + 1 - ldeg ] do
p_i := normalize( p_i * y );
p := p + p_i;
od;
p := p / const;
## it is ugly that we need this
SetIndeterminateOfUnivariateRationalFunction( p, h );
## checking this property sets it
Assert( 0, IsUnivariatePolynomial( p ) );
return CreatePolynomialModuloSomePower( p, dim );
end );
##
InstallMethod( InverseOp,
"for a Chern polynomial with rank",
[ IsChernPolynomialWithRankRep ],
function( C )
local dim, c;
dim := AmbientDimension( C );
c := TotalChernClass( C )^-1;
return CreateChernPolynomial( - Rank( C ), c );
end );
##
InstallMethod( Coefficients,
"for a polynomial modulo some power",
[ IsPolynomialModuloSomePowerRep ],
function( poly )
return CoefficientsOfUnivariatePolynomial( poly!.polynomial );
end );
##
InstallMethod( Coefficients,
"for a Chern polynomial with rank",
[ IsChernPolynomialWithRankRep ],
function( c )
local C;
C := Coefficients( TotalChernClass( c ) );
return C{[ 2 .. Length( C ) ]};
end );
##
InstallMethod( InverseOp,
"for a Chern polynomial with rank",
[ IsChernPolynomialWithRankRep and IsOne ],
IdFunc );
##
InstallMethod( Rank,
"for a Chern character",
[ IsChernCharacterRep ],
RankOfObject );
####################################
#
# constructor functions and methods:
#
####################################
##
InstallMethod( CreateElementOfGrothendieckGroupOfProjectiveSpace,
"constructor for an element of the Grothendieck group of a projective space",
[ IsHomalgModuleElement ],
function( elm )
local K_0, rank, P;
K_0 := Range( UnderlyingMorphism( elm ) );
if not IsHomalgLeftObjectOrMorphismOfLeftObjects( K_0 ) then
Error( "the Grothendieck group must be defined as a left module\n" );
elif not ( HasIsFree( K_0 ) and IsFree( K_0 ) ) then
Error( "the Grothendieck group is either not free or not known to be free\n" );
fi;
rank := Rank( K_0 );
if rank < 1 then
Error( "the rank of the Grothendieck group must be greater than 0\n" );
fi;
P := rec( );
ObjectifyWithAttributes(
P, TheTypeElementOfGrothendieckGroupOfProjectiveSpace,
UnderlyingModuleElement, elm,
GrothendieckGroup, K_0,
AmbientDimension, rank - 1,
IsZero, IsZero( elm ) );
return P;
end );
##
InstallMethod( CreateElementOfGrothendieckGroupOfProjectiveSpace,
"constructor for an element of the Grothendieck group of a projective space",
[ IsList, IsHomalgModule ],
function( coeffs, K_0 )
local rank, l;
if not IsHomalgLeftObjectOrMorphismOfLeftObjects( K_0 ) then
Error( "the Grothendieck group must be defined as a left module\n" );
fi;
rank := Rank( K_0 );
l := Length( coeffs );
if rank < l then
coeffs := coeffs{[ 1 .. rank ]};
elif rank > l then
coeffs := Concatenation( coeffs, ListWithIdenticalEntries( rank - l, 0 ) );
fi;
coeffs := HomalgMatrix( coeffs, 1, rank, HomalgRing( K_0 ) );
coeffs := HomalgModuleElement( coeffs, K_0 );
return CreateElementOfGrothendieckGroupOfProjectiveSpace( coeffs );
end );
##
InstallMethod( CreateElementOfGrothendieckGroupOfProjectiveSpace,
"constructor for an element of the Grothendieck group of a projective space",
[ IsList, IsInt ],
function( C, dim )
local ZZ, K_0;
if dim < 0 then
dim := Length( C ) - 1;
fi;
ZZ := HOMALG_MATRICES.ZZ;
K_0 := ( dim + 1 ) * ZZ;
LockObjectOnCertainPresentation( K_0 );
return CreateElementOfGrothendieckGroupOfProjectiveSpace( C, K_0 );
end );
##
InstallMethod( CreateElementOfGrothendieckGroupOfProjectiveSpace,
"constructor for an element of the Grothendieck group of a projective space",
[ IsList ],
function( C )
return CreateElementOfGrothendieckGroupOfProjectiveSpace( C, -1 );
end );
##
InstallMethod( CreateElementOfGrothendieckGroupOfProjectiveSpace,
"constructor for an element of the Grothendieck group of a projective space",
[ IsUnivariatePolynomial, IsHomalgModule ],
function( chi, K_0 )
local C, P;
C := CoefficientsOfElementOfGrothendieckGroupOfProjectiveSpace( chi );
P := CreateElementOfGrothendieckGroupOfProjectiveSpace( C, K_0 );
SetAssociatedPolynomial( P, chi );
SetIsZero( P, IsZero( chi ) );
return P;
end );
##
InstallMethod( CreateElementOfGrothendieckGroupOfProjectiveSpace,
"constructor for an element of the Grothendieck group of a projective space",
[ IsUnivariatePolynomial, IsInt ],
function( chi, dim )
local C, P;
C := CoefficientsOfElementOfGrothendieckGroupOfProjectiveSpace( chi );
P := CreateElementOfGrothendieckGroupOfProjectiveSpace( C, dim );
SetAssociatedPolynomial( P, chi );
SetIsZero( P, IsZero( chi ) );
return P;
end );
##
InstallMethod( CreateElementOfGrothendieckGroupOfProjectiveSpace,
"constructor for an element of the Grothendieck group of a projective space",
[ IsUnivariatePolynomial ],
function( chi )
return CreateElementOfGrothendieckGroupOfProjectiveSpace( chi, -1 );
end );
##
InstallMethod( CreatePolynomialModuloSomePower,
"constructor polynomials modulo some power",
[ IsUnivariatePolynomial, IsInt ],
function( poly, dim )
local h, normalize, p;
h := IndeterminateOfUnivariateRationalFunction( poly );
normalize := function( poly )
local p;
p := PolynomialReduction( poly, [ h^(dim + 1) ], MonomialLexOrdering( ) )[1];
## it is ugly that we need this
SetIndeterminateOfUnivariateRationalFunction( p, h );
## checking this property sets it
Assert( 0, IsUnivariatePolynomial( p ) );
return p;
end;
p := rec( polynomial := normalize( poly ),
indeterminate := h,
normalize := normalize );
ObjectifyWithAttributes(
p, TheTypePolynomialModuloSomePower,
AmbientDimension, dim,
IsOne, IsOne( poly ) );
return p;
end );
##
InstallMethod( CreateChernPolynomial,
"constructor of Chern polynomials with rank",
[ IsInt, IsPolynomialModuloSomePowerRep ],
function( rank, p )
local h, C;
h := p!.indeterminate;
C := rec( indeterminate := h );
ObjectifyWithAttributes(
C, TheTypeChernPolynomialWithRank,
RankOfObject, rank,
TotalChernClass, p,
AmbientDimension, AmbientDimension( p ),
IsOne, IsOne( p ) and IsZero( rank ) );
return C;
end );
##
InstallMethod( CreateChernPolynomial,
"constructor of Chern polynomials with rank",
[ IsInt, IsUnivariatePolynomial, IsInt ],
function( rank, poly, dim )
local p;
p := CreatePolynomialModuloSomePower( poly, dim );
return CreateChernPolynomial( rank, p );
end );
##
InstallMethod( CreateChernCharacter,
"constructor of Chern characters",
[ IsUnivariatePolynomial, IsInt ],
function( poly, dim )
local t, c, ch;
t := IndeterminateOfUnivariateRationalFunction( poly );
c := CreatePolynomialModuloSomePower( poly, dim );
ch := rec( indeterminate := t );
ObjectifyWithAttributes(
ch, TheTypeChernCharacter,
RankOfObject, Value( poly, 0 ),
ChernCharacterPolynomial, c,
AmbientDimension, dim,
IsZero, IsZero( poly ) );
return ch;
end );
####################################
#
# View, Print, and Display methods:
#
####################################
##
InstallMethod( ViewObj,
"for an element of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep ],
function( P )
local twisted, coeffs, l, h, i, c;
Print( "( " );
if IsBound( P!.DisplayTwistedCoefficients ) and P!.DisplayTwistedCoefficients = true then
twisted := true;
coeffs := Coefficients( P, "twisted" );
else
twisted := false;
coeffs := Coefficients( P );
fi;
l := Length( coeffs );
coeffs := Reversed( coeffs );
h := PositionNonZero( coeffs );
coeffs := coeffs{[ h .. l ]};
c := coeffs[1];
if twisted then
Print( c, "*O(", -(l - h), ")" );
else
Print( c, "*O_{P^", l - h, "}" );
fi;
for i in [ 2 .. l - h + 1 ] do
c := coeffs[i];
if not IsZero( c ) then
if c > 0 then
Print( " + " );
else
c := -c ;
Print( " - " );
fi;
if twisted then
Print( c, "*O(", -(l - h + 1 - i), ")" );
else
Print( c, "*O_{P^", l - h + 1 - i, "}" );
fi;
fi;
od;
Print( " ) -> P^", AmbientDimension( P ) );
end );
##
InstallMethod( ViewObj,
"for an element of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep and IsZero ],
function( P )
Print( "0 -> P^", AmbientDimension( P ) );
end );
##
InstallMethod( ViewObj,
"for a polynomial modulo some power",
[ IsPolynomialModuloSomePowerRep ],
function( p )
ViewObj( p!.polynomial );
end );
##
InstallMethod( ViewObj,
"for a Chern polynomial with rank",
[ IsChernPolynomialWithRankRep ],
function( C )
local c, h, coeffs, l, i;
Print( "( ", RankOfObject( C ), " | " );
c := TotalChernClass( C );
h := C!.indeterminate;
coeffs := Coefficients( c );
Print( coeffs[1] );
l := Length( coeffs );
if l > 1 and not IsZero( coeffs[2] ) then
if coeffs[2] = 1 then
Print( "+" );
elif coeffs[2] > 0 then
Print( "+", coeffs[2], "*" );
elif coeffs[2] = -1 then
Print( "-" );
elif coeffs[2] < 0 then
Print( coeffs[2], "*" );
fi;
Print( h );
fi;
for i in [ 3 .. l ] do
if not IsZero( coeffs[i] ) then
if coeffs[i] = 1 then
Print( "+" );
elif coeffs[i] > 0 then
Print( "+", coeffs[i], "*" );
elif coeffs[i] = -1 then
Print( "-" );
elif coeffs[i] < 0 then
Print( coeffs[i], "*" );
fi;
Print( h, "^", i - 1 );
fi;
od;
Print( " ) -> P^", AmbientDimension( C ) );
end );
##
InstallMethod( Name,
"for a Chern polynomial with rank",
[ IsChernPolynomialWithRankRep ],
function( C )
local c, h, coeffs, l, i, name;
name := "";
Append( name, Concatenation( "( ", String( RankOfObject( C ) ), " | " ) );
c := TotalChernClass( C );
h := C!.indeterminate;
coeffs := Coefficients( c );
Append( name, String( coeffs[1] ) );
l := Length( coeffs );
if l > 1 and not IsZero( coeffs[2] ) then
if coeffs[2] = 1 then
Append( name, "+" );
elif coeffs[2] > 0 then
Append( name, Concatenation( "+", String( coeffs[2] ), "*" ) );
elif coeffs[2] = -1 then
Append( name, "-" );
elif coeffs[2] < 0 then
Append( name, Concatenation( String( coeffs[2] ), "*" ) );
fi;
Append( name, String( h ) );
fi;
for i in [ 3 .. l ] do
if not IsZero( coeffs[i] ) then
if coeffs[i] = 1 then
Append( name, "+" );
elif coeffs[i] > 0 then
Append( name, Concatenation( "+", String( coeffs[i] ), "*" ) );
elif coeffs[i] = -1 then
Append( name, "-" );
elif coeffs[i] < 0 then
Append( name, Concatenation( String( coeffs[i] ), "*" ) );
fi;
Append( name, Concatenation( String( h ), "^", String( i - 1 ) ) );
fi;
od;
Append( name, Concatenation( " ) -> P^", String( AmbientDimension( C ) ) ) );
return name;
end );
##
InstallMethod( ViewObj,
"for a Chern character",
[ IsChernCharacterRep ],
function( ch )
local c, t, coeffs, l, i;
Print( "[ " );
c := ChernCharacterPolynomial( ch );
t := ch!.indeterminate;
coeffs := Coefficients( c );
l := Length( coeffs );
coeffs := List( [ 0 .. l - 1 ], i -> coeffs[i + 1] * Factorial( i ) );
Print( coeffs[1] );
if l > 1 and not IsZero( coeffs[2] ) then
if coeffs[2] = 1 then
Print( "+" );
elif coeffs[2] > 0 then
Print( "+", coeffs[2], "*" );
elif coeffs[2] = -1 then
Print( "-" );
elif coeffs[2] < 0 then
Print( coeffs[2], "*" );
fi;
Print( t );
fi;
for i in [ 3 .. l ] do
if not IsZero( coeffs[i] ) then
if coeffs[i] = 1 then
Print( "+" );
elif coeffs[i] > 0 then
Print( "+", coeffs[i], "*" );
elif coeffs[i] = -1 then
Print( "-" );
elif coeffs[i] < 0 then
Print( coeffs[i], "*" );
fi;
Print( t, "^", i - 1, "/", i - 1, "!" );
fi;
od;
Print( " ] -> P^", AmbientDimension( ch ) );
end );
##
InstallMethod( ViewObj,
"for a Chern character",
[ IsChernCharacterRep and IsZero ],
function( ch )
Print( "0 -> P^", AmbientDimension( ch ) );
end );
##
InstallMethod( Display,
"for an element of the Grothendieck group of a projective space",
[ IsElementOfGrothendieckGroupOfProjectiveSpaceRep ],
function( P )
ViewObj( P ); Print( "\n" );
end );
![swh spinner](/static/img/swh-spinner.gif)
Computing file changes ...