Ejemplo n.º 1
0
    def __init__(self, parent, polys, check=True):
        r"""
        The Python constructor.

        See :class:`SchemeMorphism_polynomial` for details.

        INPUT:

        - ``parent`` -- Hom

        - ``polys`` -- list or tuple of polynomial or rational functions

        - ``check`` -- Boolean

        OUTPUT:

        - :class:`SchemeMorphism_polynomial_affine_space`

        EXAMPLES::

            sage: A.<x,y>=AffineSpace(ZZ,2)
            sage: H=Hom(A,A)
            sage: H([3/5*x^2,y^2/(2*x^2)])
            Traceback (most recent call last):
            ...
            TypeError: polys (=[3/5*x^2, y^2/(2*x^2)]) must be rational functions in
            Multivariate Polynomial Ring in x, y over Integer Ring

        ::

            sage: A.<x,y>=AffineSpace(ZZ,2)
            sage: H=Hom(A,A)
            sage: H([3*x^2/(5*y),y^2/(2*x^2)])
            Scheme endomorphism of Affine Space of dimension 2 over Integer Ring
              Defn: Defined on coordinates by sending (x, y) to
                    (3*x^2/(5*y), y^2/(2*x^2))


            sage: A.<x,y>=AffineSpace(QQ,2)
            sage: H=Hom(A,A)
            sage: H([3/2*x^2,y^2])
            Scheme endomorphism of Affine Space of dimension 2 over Rational Field
              Defn: Defined on coordinates by sending (x, y) to
                    (3/2*x^2, y^2)


            sage: A.<x,y>=AffineSpace(QQ,2)
            sage: X=A.subscheme([x-y^2])
            sage: H=Hom(X,X)
            sage: H([9/4*x^2,3/2*y])
            Scheme endomorphism of Closed subscheme of Affine Space of dimension 2
            over Rational Field defined by:
              -y^2 + x
              Defn: Defined on coordinates by sending (x, y) to
                    (9/4*x^2, 3/2*y)

            sage: P.<x,y,z>=ProjectiveSpace(ZZ,2)
            sage: H=Hom(P,P)
            sage: f=H([5*x^3 + 3*x*y^2-y^3,3*z^3 + y*x^2, x^3-z^3])
            sage: f.dehomogenize(2)
            Scheme endomorphism of Affine Space of dimension 2 over Integer Ring
              Defn: Defined on coordinates by sending (x0, x1) to
                    ((5*x0^3 + 3*x0*x1^2 - x1^3)/(x0^3 - 1), (x0^2*x1 + 3)/(x0^3 - 1))
        """
        if check:
            if not isinstance(polys, (list, tuple)):
                raise TypeError("polys (=%s) must be a list or tuple" % polys)
            source_ring = parent.domain().ambient_space().coordinate_ring()
            target = parent.codomain().ambient_space()
            if len(polys) != target.ngens():
                raise ValueError("there must be %s polynomials" %
                                 target.ngens())
            try:
                polys = [source_ring(poly) for poly in polys]
            except TypeError:
                if all(p.base_ring() == source_ring.base_ring()
                       for p in polys) == False:
                    raise TypeError(
                        "polys (=%s) must be rational functions in %s" %
                        (polys, source_ring))
                try:
                    polys = [
                        source_ring(poly.numerator()) /
                        source_ring(poly.denominator()) for poly in polys
                    ]
                except TypeError:
                    raise TypeError(
                        "polys (=%s) must be rational functions in %s" %
                        (polys, source_ring))
            if isinstance(source_ring, QuotientRing_generic):
                polys = [f.lift() for f in polys]
        self._is_prime_finite_field = is_PrimeFiniteField(
            polys[0].base_ring())  # Needed for _fast_eval and _fastpolys
        SchemeMorphism_polynomial.__init__(self, parent, polys, False)
Ejemplo n.º 2
0
def Conic(base_field, F=None, names=None, unique=True):
    r"""
    Return the plane projective conic curve defined by ``F``
    over ``base_field``.

    The input form ``Conic(F, names=None)`` is also accepted,
    in which case the fraction field of the base ring of ``F``
    is used as base field.

    INPUT:

    - ``base_field`` -- The base field of the conic.

    - ``names`` -- a list, tuple, or comma separated string
      of three variable names specifying the names
      of the coordinate functions of the ambient
      space `\Bold{P}^3`. If not specified or read
      off from ``F``, then this defaults to ``'x,y,z'``.

    - ``F`` -- a polynomial, list, matrix, ternary quadratic form,
      or list or tuple of 5 points in the plane.

                   If ``F`` is a polynomial or quadratic form,
                   then the output is the curve in the projective plane
                   defined by ``F = 0``.

                   If ``F`` is a polynomial, then it must be a polynomial
                   of degree at most 2 in 2 variables, or a homogeneous
                   polynomial in of degree 2 in 3 variables.

                   If ``F`` is a matrix, then the output is the zero locus
                   of `(x,y,z) F (x,y,z)^t`.

                   If ``F`` is a list of coefficients, then it has
                   length 3 or 6 and gives the coefficients of
                   the monomials `x^2, y^2, z^2` or all 6 monomials
                   `x^2, xy, xz, y^2, yz, z^2` in lexicographic order.

                   If ``F`` is a list of 5 points in the plane, then the output
                   is a conic through those points.

    - ``unique`` -- Used only if ``F`` is a list of points in the plane.
      If the conic through the points is not unique, then
      raise ``ValueError`` if and only if ``unique`` is True

    OUTPUT:

    A plane projective conic curve defined by ``F`` over a field.

    EXAMPLES:

    Conic curves given by polynomials ::

        sage: X,Y,Z = QQ['X,Y,Z'].gens()
        sage: Conic(X^2 - X*Y + Y^2 - Z^2)
        Projective Conic Curve over Rational Field defined by X^2 - X*Y + Y^2 - Z^2
        sage: x,y = GF(7)['x,y'].gens()
        sage: Conic(x^2 - x + 2*y^2 - 3, 'U,V,W')
        Projective Conic Curve over Finite Field of size 7 defined by U^2 + 2*V^2 - U*W - 3*W^2

    Conic curves given by matrices ::

        sage: Conic(matrix(QQ, [[1, 2, 0], [4, 0, 0], [7, 0, 9]]), 'x,y,z')
        Projective Conic Curve over Rational Field defined by x^2 + 6*x*y + 7*x*z + 9*z^2

        sage: x,y,z = GF(11)['x,y,z'].gens()
        sage: C = Conic(x^2+y^2-2*z^2); C
        Projective Conic Curve over Finite Field of size 11 defined by x^2 + y^2 - 2*z^2
        sage: Conic(C.symmetric_matrix(), 'x,y,z')
        Projective Conic Curve over Finite Field of size 11 defined by x^2 + y^2 - 2*z^2

    Conics given by coefficients ::

        sage: Conic(QQ, [1,2,3])
        Projective Conic Curve over Rational Field defined by x^2 + 2*y^2 + 3*z^2
        sage: Conic(GF(7), [1,2,3,4,5,6], 'X')
        Projective Conic Curve over Finite Field of size 7 defined by X0^2 + 2*X0*X1 - 3*X1^2 + 3*X0*X2 - 2*X1*X2 - X2^2

    The conic through a set of points ::

        sage: C = Conic(QQ, [[10,2],[3,4],[-7,6],[7,8],[9,10]]); C
        Projective Conic Curve over Rational Field defined by x^2 + 13/4*x*y - 17/4*y^2 - 35/2*x*z + 91/4*y*z - 37/2*z^2
        sage: C.rational_point()
        (10 : 2 : 1)
        sage: C.point([3,4])
        (3 : 4 : 1)

        sage: a=AffineSpace(GF(13),2)
        sage: Conic([a([x,x^2]) for x in range(5)])
        Projective Conic Curve over Finite Field of size 13 defined by x^2 - y*z
    """
    if not (is_IntegralDomain(base_field) or base_field is None):
        if names is None:
            names = F
        F = base_field
        base_field = None
    if isinstance(F, (list, tuple)):
        if len(F) == 1:
            return Conic(base_field, F[0], names)
        if names is None:
            names = "x,y,z"
        if len(F) == 5:
            L = []
            for f in F:
                if isinstance(f, SchemeMorphism_point_affine):
                    C = Sequence(f, universe=base_field)
                    if len(C) != 2:
                        raise TypeError("points in F (=%s) must be planar" % F)
                    C.append(1)
                elif isinstance(f, SchemeMorphism_point_projective_field):
                    C = Sequence(f, universe=base_field)
                elif isinstance(f, (list, tuple)):
                    C = Sequence(f, universe=base_field)
                    if len(C) == 2:
                        C.append(1)
                else:
                    raise TypeError("F (=%s) must be a sequence of planar " "points" % F)
                if len(C) != 3:
                    raise TypeError("points in F (=%s) must be planar" % F)
                P = C.universe()
                if not is_IntegralDomain(P):
                    raise TypeError("coordinates of points in F (=%s) must " "be in an integral domain" % F)
                L.append(
                    Sequence(
                        [C[0] ** 2, C[0] * C[1], C[0] * C[2], C[1] ** 2, C[1] * C[2], C[2] ** 2], P.fraction_field()
                    )
                )
            M = Matrix(L)
            if unique and M.rank() != 5:
                raise ValueError("points in F (=%s) do not define a unique " "conic" % F)
            con = Conic(base_field, Sequence(M.right_kernel().gen()), names)
            con.point(F[0])
            return con
        F = Sequence(F, universe=base_field)
        base_field = F.universe().fraction_field()
        temp_ring = PolynomialRing(base_field, 3, names)
        (x, y, z) = temp_ring.gens()
        if len(F) == 3:
            return Conic(F[0] * x ** 2 + F[1] * y ** 2 + F[2] * z ** 2)
        if len(F) == 6:
            return Conic(F[0] * x ** 2 + F[1] * x * y + F[2] * x * z + F[3] * y ** 2 + F[4] * y * z + F[5] * z ** 2)
        raise TypeError("F (=%s) must be a sequence of 3 or 6" "coefficients" % F)
    if is_QuadraticForm(F):
        F = F.matrix()
    if is_Matrix(F) and F.is_square() and F.ncols() == 3:
        if names is None:
            names = "x,y,z"
        temp_ring = PolynomialRing(F.base_ring(), 3, names)
        F = vector(temp_ring.gens()) * F * vector(temp_ring.gens())

    if not is_MPolynomial(F):
        raise TypeError("F (=%s) must be a three-variable polynomial or " "a sequence of points or coefficients" % F)

    if F.total_degree() != 2:
        raise TypeError("F (=%s) must have degree 2" % F)

    if base_field is None:
        base_field = F.base_ring()
    if not is_IntegralDomain(base_field):
        raise ValueError("Base field (=%s) must be a field" % base_field)
    base_field = base_field.fraction_field()
    if names is None:
        names = F.parent().variable_names()
    pol_ring = PolynomialRing(base_field, 3, names)

    if F.parent().ngens() == 2:
        (x, y, z) = pol_ring.gens()
        F = pol_ring(F(x / z, y / z) * z ** 2)

    if F == 0:
        raise ValueError("F must be nonzero over base field %s" % base_field)

    if F.total_degree() != 2:
        raise TypeError("F (=%s) must have degree 2 over base field %s" % (F, base_field))

    if F.parent().ngens() == 3:
        P2 = ProjectiveSpace(2, base_field, names)
        if is_PrimeFiniteField(base_field):
            return ProjectiveConic_prime_finite_field(P2, F)
        if is_FiniteField(base_field):
            return ProjectiveConic_finite_field(P2, F)
        if is_RationalField(base_field):
            return ProjectiveConic_rational_field(P2, F)
        if is_NumberField(base_field):
            return ProjectiveConic_number_field(P2, F)
        return ProjectiveConic_field(P2, F)

    raise TypeError("Number of variables of F (=%s) must be 2 or 3" % F)
Ejemplo n.º 3
0
def Conic(base_field, F=None, names=None, unique=True):
    r"""
    Return the plane projective conic curve defined by ``F``
    over ``base_field``.

    The input form ``Conic(F, names=None)`` is also accepted,
    in which case the fraction field of the base ring of ``F``
    is used as base field.

    INPUT:

    - ``base_field`` -- The base field of the conic.

    - ``names`` -- a list, tuple, or comma separated string
      of three variable names specifying the names
      of the coordinate functions of the ambient
      space `\Bold{P}^3`. If not specified or read
      off from ``F``, then this defaults to ``'x,y,z'``.

    - ``F`` -- a polynomial, list, matrix, ternary quadratic form,
      or list or tuple of 5 points in the plane.

                   If ``F`` is a polynomial or quadratic form,
                   then the output is the curve in the projective plane
                   defined by ``F = 0``.

                   If ``F`` is a polynomial, then it must be a polynomial
                   of degree at most 2 in 2 variables, or a homogeneous
                   polynomial in of degree 2 in 3 variables.

                   If ``F`` is a matrix, then the output is the zero locus
                   of `(x,y,z) F (x,y,z)^t`.

                   If ``F`` is a list of coefficients, then it has
                   length 3 or 6 and gives the coefficients of
                   the monomials `x^2, y^2, z^2` or all 6 monomials
                   `x^2, xy, xz, y^2, yz, z^2` in lexicographic order.

                   If ``F`` is a list of 5 points in the plane, then the output
                   is a conic through those points.

    - ``unique`` -- Used only if ``F`` is a list of points in the plane.
      If the conic through the points is not unique, then
      raise ``ValueError`` if and only if ``unique`` is True

    OUTPUT:

    A plane projective conic curve defined by ``F`` over a field.

    EXAMPLES:

    Conic curves given by polynomials ::

        sage: X,Y,Z = QQ['X,Y,Z'].gens()
        sage: Conic(X^2 - X*Y + Y^2 - Z^2)
        Projective Conic Curve over Rational Field defined by X^2 - X*Y + Y^2 - Z^2
        sage: x,y = GF(7)['x,y'].gens()
        sage: Conic(x^2 - x + 2*y^2 - 3, 'U,V,W')
        Projective Conic Curve over Finite Field of size 7 defined by U^2 + 2*V^2 - U*W - 3*W^2

    Conic curves given by matrices ::

        sage: Conic(matrix(QQ, [[1, 2, 0], [4, 0, 0], [7, 0, 9]]), 'x,y,z')
        Projective Conic Curve over Rational Field defined by x^2 + 6*x*y + 7*x*z + 9*z^2

        sage: x,y,z = GF(11)['x,y,z'].gens()
        sage: C = Conic(x^2+y^2-2*z^2); C
        Projective Conic Curve over Finite Field of size 11 defined by x^2 + y^2 - 2*z^2
        sage: Conic(C.symmetric_matrix(), 'x,y,z')
        Projective Conic Curve over Finite Field of size 11 defined by x^2 + y^2 - 2*z^2

    Conics given by coefficients ::

        sage: Conic(QQ, [1,2,3])
        Projective Conic Curve over Rational Field defined by x^2 + 2*y^2 + 3*z^2
        sage: Conic(GF(7), [1,2,3,4,5,6], 'X')
        Projective Conic Curve over Finite Field of size 7 defined by X0^2 + 2*X0*X1 - 3*X1^2 + 3*X0*X2 - 2*X1*X2 - X2^2

    The conic through a set of points ::

        sage: C = Conic(QQ, [[10,2],[3,4],[-7,6],[7,8],[9,10]]); C
        Projective Conic Curve over Rational Field defined by x^2 + 13/4*x*y - 17/4*y^2 - 35/2*x*z + 91/4*y*z - 37/2*z^2
        sage: C.rational_point()
        (10 : 2 : 1)
        sage: C.point([3,4])
        (3 : 4 : 1)

        sage: a=AffineSpace(GF(13),2)
        sage: Conic([a([x,x^2]) for x in range(5)])
        Projective Conic Curve over Finite Field of size 13 defined by x^2 - y*z
    """
    if not (is_IntegralDomain(base_field) or base_field is None):
        if names is None:
            names = F
        F = base_field
        base_field = None
    if isinstance(F, (list, tuple)):
        if len(F) == 1:
            return Conic(base_field, F[0], names)
        if names is None:
            names = 'x,y,z'
        if len(F) == 5:
            L = []
            for f in F:
                if isinstance(f, SchemeMorphism_point_affine):
                    C = Sequence(f, universe=base_field)
                    if len(C) != 2:
                        raise TypeError("points in F (=%s) must be planar" % F)
                    C.append(1)
                elif isinstance(f, SchemeMorphism_point_projective_field):
                    C = Sequence(f, universe=base_field)
                elif isinstance(f, (list, tuple)):
                    C = Sequence(f, universe=base_field)
                    if len(C) == 2:
                        C.append(1)
                else:
                    raise TypeError("F (=%s) must be a sequence of planar " \
                                      "points" % F)
                if len(C) != 3:
                    raise TypeError("points in F (=%s) must be planar" % F)
                P = C.universe()
                if not is_IntegralDomain(P):
                    raise TypeError("coordinates of points in F (=%s) must " \
                                     "be in an integral domain" % F)
                L.append(
                    Sequence([
                        C[0]**2, C[0] * C[1], C[0] * C[2], C[1]**2,
                        C[1] * C[2], C[2]**2
                    ], P.fraction_field()))
            M = Matrix(L)
            if unique and M.rank() != 5:
                raise ValueError("points in F (=%s) do not define a unique " \
                                   "conic" % F)
            con = Conic(base_field, Sequence(M.right_kernel().gen()), names)
            con.point(F[0])
            return con
        F = Sequence(F, universe=base_field)
        base_field = F.universe().fraction_field()
        temp_ring = PolynomialRing(base_field, 3, names)
        (x, y, z) = temp_ring.gens()
        if len(F) == 3:
            return Conic(F[0] * x**2 + F[1] * y**2 + F[2] * z**2)
        if len(F) == 6:
            return Conic(F[0]*x**2 + F[1]*x*y + F[2]*x*z + F[3]*y**2 + \
                         F[4]*y*z + F[5]*z**2)
        raise TypeError("F (=%s) must be a sequence of 3 or 6" \
                         "coefficients" % F)
    if is_QuadraticForm(F):
        F = F.matrix()
    if is_Matrix(F) and F.is_square() and F.ncols() == 3:
        if names is None:
            names = 'x,y,z'
        temp_ring = PolynomialRing(F.base_ring(), 3, names)
        F = vector(temp_ring.gens()) * F * vector(temp_ring.gens())

    if not is_MPolynomial(F):
        raise TypeError("F (=%s) must be a three-variable polynomial or " \
                         "a sequence of points or coefficients" % F)

    if F.total_degree() != 2:
        raise TypeError("F (=%s) must have degree 2" % F)

    if base_field is None:
        base_field = F.base_ring()
    if not is_IntegralDomain(base_field):
        raise ValueError("Base field (=%s) must be a field" % base_field)
    base_field = base_field.fraction_field()
    if names is None:
        names = F.parent().variable_names()
    pol_ring = PolynomialRing(base_field, 3, names)

    if F.parent().ngens() == 2:
        (x, y, z) = pol_ring.gens()
        F = pol_ring(F(x / z, y / z) * z**2)

    if F == 0:
        raise ValueError("F must be nonzero over base field %s" % base_field)

    if F.total_degree() != 2:
        raise TypeError("F (=%s) must have degree 2 over base field %s" % \
                          (F, base_field))

    if F.parent().ngens() == 3:
        P2 = ProjectiveSpace(2, base_field, names)
        if is_PrimeFiniteField(base_field):
            return ProjectiveConic_prime_finite_field(P2, F)
        if is_FiniteField(base_field):
            return ProjectiveConic_finite_field(P2, F)
        if is_RationalField(base_field):
            return ProjectiveConic_rational_field(P2, F)
        if is_NumberField(base_field):
            return ProjectiveConic_number_field(P2, F)
        return ProjectiveConic_field(P2, F)

    raise TypeError("Number of variables of F (=%s) must be 2 or 3" % F)
Ejemplo n.º 4
0
    def __init__(self, parent, polys, check=True):
        r"""
        The Python constructor.

        See :class:`SchemeMorphism_polynomial` for details.

        INPUT:

        - ``parent`` -- Hom

        - ``polys`` -- list or tuple of polynomial or rational functions

        - ``check`` -- Boolean

        OUTPUT:

        - :class:`SchemeMorphism_polynomial_affine_space`

        EXAMPLES::

            sage: A.<x,y>=AffineSpace(ZZ,2)
            sage: H=Hom(A,A)
            sage: H([3/5*x^2,y^2/(2*x^2)])
            Traceback (most recent call last):
            ...
            TypeError: polys (=[3/5*x^2, y^2/(2*x^2)]) must be rational functions in
            Multivariate Polynomial Ring in x, y over Integer Ring

        ::

            sage: A.<x,y>=AffineSpace(ZZ,2)
            sage: H=Hom(A,A)
            sage: H([3*x^2/(5*y),y^2/(2*x^2)])
            Scheme endomorphism of Affine Space of dimension 2 over Integer Ring
              Defn: Defined on coordinates by sending (x, y) to
                    (3*x^2/(5*y), y^2/(2*x^2))


            sage: A.<x,y>=AffineSpace(QQ,2)
            sage: H=Hom(A,A)
            sage: H([3/2*x^2,y^2])
            Scheme endomorphism of Affine Space of dimension 2 over Rational Field
              Defn: Defined on coordinates by sending (x, y) to
                    (3/2*x^2, y^2)


            sage: A.<x,y>=AffineSpace(QQ,2)
            sage: X=A.subscheme([x-y^2])
            sage: H=Hom(X,X)
            sage: H([9/4*x^2,3/2*y])
            Scheme endomorphism of Closed subscheme of Affine Space of dimension 2
            over Rational Field defined by:
              -y^2 + x
              Defn: Defined on coordinates by sending (x, y) to
                    (9/4*x^2, 3/2*y)

            sage: P.<x,y,z>=ProjectiveSpace(ZZ,2)
            sage: H=Hom(P,P)
            sage: f=H([5*x^3 + 3*x*y^2-y^3,3*z^3 + y*x^2, x^3-z^3])
            sage: f.dehomogenize(2)
            Scheme endomorphism of Affine Space of dimension 2 over Integer Ring
              Defn: Defined on coordinates by sending (x0, x1) to
                    ((5*x0^3 + 3*x0*x1^2 - x1^3)/(x0^3 - 1), (x0^2*x1 + 3)/(x0^3 - 1))
        """
        if check:
            if not isinstance(polys, (list, tuple)):
                raise TypeError("polys (=%s) must be a list or tuple"%polys)
            source_ring =parent.domain().ambient_space().coordinate_ring()
            target = parent.codomain().ambient_space()
            if len(polys) != target.ngens():
                raise ValueError("there must be %s polynomials"%target.ngens())
            try:
                polys = [source_ring(poly) for poly in polys]
            except TypeError:
                if all(p.base_ring()==source_ring.base_ring() for p in polys)==False:
                    raise TypeError("polys (=%s) must be rational functions in %s"%(polys,source_ring))
                try:
                    polys = [source_ring(poly.numerator())/source_ring(poly.denominator()) for poly in polys]
                except TypeError:
                    raise TypeError("polys (=%s) must be rational functions in %s"%(polys,source_ring))
            if isinstance(source_ring, QuotientRing_generic):
                polys = [f.lift() for f in polys]
        self._is_prime_finite_field = is_PrimeFiniteField(polys[0].base_ring()) # Needed for _fast_eval and _fastpolys
        SchemeMorphism_polynomial.__init__(self, parent,polys, False)