Exemple #1
0
    def __init__(self,
                 V,
                 W,
                 gens=None,
                 modulus=None,
                 modulus_qf=None,
                 check=True):
        r"""
        Initialize ``self``.

        TESTS::

            sage: from sage.modules.torsion_quadratic_module import TorsionQuadraticModule
            sage: T = TorsionQuadraticModule(ZZ^3, 6*ZZ^3)
            sage: TestSuite(T).run()
        """
        if check:
            if V.rank() != W.rank():
                raise ValueError("modules must be of the same rank")
            if V.base_ring() is not ZZ:
                raise NotImplementedError("only currently implemented over ZZ")
            if V.inner_product_matrix() != V.inner_product_matrix().transpose(
            ):
                raise ValueError(
                    "the cover must have a symmetric inner product")

            if gens is not None and V.span(gens) + W != V:
                raise ValueError("provided gens do not generate the quotient")

        FGP_Module_class.__init__(self, V, W, check=check)
        if gens is not None:
            self._gens_user = tuple(self(v) for v in gens)
        else:
            # this is taken care of in the .gens method
            # we do not want this at initialization
            self._gens_user = None

        # compute the modulus - this may be expensive
        if modulus is None or check:
            # The inner product of two elements `b(v1+W,v2+W)`
            # is defined `mod (V,W)`
            num = V.basis_matrix() * V.inner_product_matrix() * W.basis_matrix(
            ).T
            self._modulus = gcd(num.list())

        if modulus is not None:
            if check and self._modulus / modulus not in self.base_ring():
                raise ValueError("the modulus must divide (V, W)")
            self._modulus = modulus

        if modulus_qf is None or check:
            # The quadratic_product of an element `q(v+W)` is defined
            # `\mod 2(V,W) + ZZ\{ (w,w) | w in w\}`
            norm = gcd(self.W().gram_matrix().diagonal())
            self._modulus_qf = gcd(norm, 2 * self._modulus)

        if modulus_qf is not None:
            if check and self._modulus_qf / modulus_qf not in self.base_ring():
                raise ValueError("the modulus_qf must divide (V, W)")
            self._modulus_qf = modulus_qf
    def __init__(self, cover, relations):
        r"""
        EXAMPLES::

            sage: G = AdditiveAbelianGroup([0]); G # indirect doctest
            Additive abelian group isomorphic to Z
            sage: G == loads(dumps(G))
            True
        """
        FGP_Module_class.__init__(self, cover, relations)
    def __init__(self, cover, relations):
        r"""
        EXAMPLE::

            sage: G = AdditiveAbelianGroup([0]); G # indirect doctest
            Additive abelian group isomorphic to Z
            sage: G == loads(dumps(G))
            True
        """
        FGP_Module_class.__init__(self, cover, relations)
    def __init__(self, V, W, gens=None, modulus=None, modulus_qf=None, check=True):
        r"""
        Initialize ``self``.

        TESTS::

            sage: from sage.modules.torsion_quadratic_module import TorsionQuadraticModule
            sage: T = TorsionQuadraticModule(ZZ^3, 6*ZZ^3)
            sage: TestSuite(T).run()
        """
        if check:
            if V.rank() != W.rank():
                raise ValueError("modules must be of the same rank")
            if V.base_ring() is not ZZ:
                raise NotImplementedError("only currently implemented over ZZ")
            if V.inner_product_matrix() != V.inner_product_matrix().transpose():
                raise ValueError("the cover must have a symmetric inner product")

            if gens is not None and V.span(gens) + W != V:
                raise ValueError("provided gens do not generate the quotient")

        FGP_Module_class.__init__(self, V, W, check=check)
        if gens is None:
            self._gens = FGP_Module_class.gens(self)
        else:
            self._gens = [self(v) for v in gens]

        if modulus is not None:
            if check:
                # The inner product of two elements `b(v1+W,v2+W)` is defined `mod (V,W)`
                num = gcd([x.inner_product(y) for x in V.gens()
                           for y in W.gens()])
                if num / modulus not in self.base_ring():
                    raise ValueError("the modulus must divide (V, W)")
            self._modulus = modulus
        else:
            # The inner product of two elements `b(v1+W,v2+W)` is defined `mod (V,W)`
            self._modulus = gcd([x.inner_product(y) for x in V.gens()
                                 for y in W.gens()])


        if modulus_qf is not None:
            if check:
                # The quadratic_product of an element `q(v+W)` is defined
                # `\mod 2(V,W) + ZZ\{ (w,w) | w in w\}`
                norm = gcd(self.W().gram_matrix().diagonal())
                num = gcd(norm, 2 * self._modulus)
                if num / modulus_qf not in self.base_ring():
                    raise ValueError("the modulus_qf must divide (V, W)")
            self._modulus_qf = modulus_qf
        else:
            # The quadratic_product of an element `q(v+W)` is defined
            # `\mod 2(V,W) + ZZ\{ (w,w) | w in w\}`
            norm = gcd(self.W().gram_matrix().diagonal())
            self._modulus_qf = gcd(norm, 2 * self._modulus)
Exemple #5
0
    def __init__(self, V, W, gens, modulus, modulus_qf):
        r"""
        Initialize ``self``.

        TESTS::

            sage: from sage.modules.torsion_quadratic_module import TorsionQuadraticModule
            sage: T = TorsionQuadraticModule(ZZ^3, 6*ZZ^3)
            sage: TestSuite(T).run()
        """

        FGP_Module_class.__init__(self, V, W, check=True)
        if gens is not None:
            self._gens_user = tuple(self(g) for g in gens)
        else:
            # this is taken care of in the .gens method
            # we do not want this at initialization
            self._gens_user = None
        self._modulus = modulus
        self._modulus_qf = modulus_qf
    def submodule(self, x):
        r"""
        Return the submodule defined by ``x``.

        The modulus of the inner product is inherited from ``self``.

        INPUT:

        - ``x`` -- list, tuple, or FGP module

        OUTPUT:

        - a :class:`TorsionQuadraticModule`

        EXAMPLES::

            sage: from sage.modules.torsion_quadratic_module import TorsionQuadraticModule
            sage: V = FreeQuadraticModule(ZZ,3,matrix.identity(3)*5)
            sage: T = TorsionQuadraticModule((1/5)*V, V)
            sage: T
            Finite quadratic module over Integer Ring with invariants (5, 5, 5)
            Gram matrix of the quadratic form with values in Q/Z:
            [1/5   0   0]
            [  0 1/5   0]
            [  0   0 1/5]
            sage: T.submodule(T.gens()[:2])
            Finite quadratic module over Integer Ring with invariants (5, 5)
            Gram matrix of the quadratic form with values in Q/Z:
            [1/5   0]
            [  0 1/5]
        """
        T = FGP_Module_class.submodule(self, x)
        # We need to explicitly set the _modulus and _modulus_qf
        #   else the modulus might increase.
        T._modulus = self._modulus
        T._modulus_qf = self._modulus_qf
        return T
Exemple #7
0
    def submodule(self, x):
        r"""
        Return the submodule defined by ``x``.

        The modulus of the inner product is inherited from ``self``.

        INPUT:

        - ``x`` -- list, tuple, or FGP module

        OUTPUT:

        - a :class:`TorsionQuadraticModule`

        EXAMPLES::

            sage: from sage.modules.torsion_quadratic_module import TorsionQuadraticModule
            sage: V = FreeQuadraticModule(ZZ,3,matrix.identity(3)*5)
            sage: T = TorsionQuadraticModule((1/5)*V, V)
            sage: T
            Finite quadratic module over Integer Ring with invariants (5, 5, 5)
            Gram matrix of the quadratic form with values in Q/Z:
            [1/5   0   0]
            [  0 1/5   0]
            [  0   0 1/5]
            sage: T.submodule(T.gens()[:2])
            Finite quadratic module over Integer Ring with invariants (5, 5)
            Gram matrix of the quadratic form with values in Q/Z:
            [1/5   0]
            [  0 1/5]
        """
        T = FGP_Module_class.submodule(self, x)
        # We need to explicitly set the _modulus and _modulus_qf
        #   else the modulus might increase.
        T._modulus = self._modulus
        T._modulus_qf = self._modulus_qf
        return T
Exemple #8
0
    def __init__(self,
                 V,
                 W,
                 gens=None,
                 modulus=None,
                 modulus_qf=None,
                 check=True):
        r"""
        Initialize ``self``.

        TESTS::

            sage: from sage.modules.torsion_quadratic_module import TorsionQuadraticModule
            sage: T = TorsionQuadraticModule(ZZ^3, 6*ZZ^3)
            sage: TestSuite(T).run()
        """
        if check:
            if V.rank() != W.rank():
                raise ValueError("modules must be of the same rank")
            if V.base_ring() is not ZZ:
                raise NotImplementedError("only currently implemented over ZZ")
            if V.inner_product_matrix() != V.inner_product_matrix().transpose(
            ):
                raise ValueError(
                    "the cover must have a symmetric inner product")

            if gens is not None and V.span(gens) + W != V:
                raise ValueError("provided gens do not generate the quotient")

        FGP_Module_class.__init__(self, V, W, check=check)
        if gens is None:
            self._gens = FGP_Module_class.gens(self)
        else:
            self._gens = [self(v) for v in gens]

        if modulus is not None:
            if check:
                # The inner product of two elements `b(v1+W,v2+W)` is defined `mod (V,W)`
                num = gcd(
                    [x.inner_product(y) for x in V.gens() for y in W.gens()])
                if num / modulus not in self.base_ring():
                    raise ValueError("the modulus must divide (V, W)")
            self._modulus = modulus
        else:
            # The inner product of two elements `b(v1+W,v2+W)` is defined `mod (V,W)`
            self._modulus = gcd(
                [x.inner_product(y) for x in V.gens() for y in W.gens()])

        if modulus_qf is not None:
            if check:
                # The quadratic_product of an element `q(v+W)` is defined
                # `\mod 2(V,W) + ZZ\{ (w,w) | w in w\}`
                norm = gcd(self.W().gram_matrix().diagonal())
                num = gcd(norm, 2 * self._modulus)
                if num / modulus_qf not in self.base_ring():
                    raise ValueError("the modulus_qf must divide (V, W)")
            self._modulus_qf = modulus_qf
        else:
            # The quadratic_product of an element `q(v+W)` is defined
            # `\mod 2(V,W) + ZZ\{ (w,w) | w in w\}`
            norm = gcd(self.W().gram_matrix().diagonal())
            self._modulus_qf = gcd(norm, 2 * self._modulus)