a
    Ÿ¬<b¿  ã                   @   sš   d Z ddlmZmZ ddlmZmZmZmZm	Z	m
Z
 ddlmZ ddlmZ ddlmZ ddlmZ ddlmZ dd	lZeG d
d„ deeeƒƒZeƒ Zd	S )z.Implementation of :class:`IntegerRing` class. é    )ÚMPZÚHAS_GMPY)ÚSymPyIntegerÚ	factorialÚgcdexÚgcdÚlcmÚsqrt)ÚCharacteristicZero)ÚRing)ÚSimpleDomain)ÚCoercionFailed)ÚpublicNc                   @   s  e Zd ZdZdZdZeZedƒZedƒZ	e
e	ƒZd ZZdZdZdZdZdd„ Zdd	„ Zd
d„ Zdd„ Zdd„ Zdd„ Zdd„ Zdd„ Zdd„ Zdd„ Zdd„ Zdd„ Zdd„ Zd d!„ Zd"d#„ Z d$d%„ Z!d&d'„ Z"d(d)„ Z#d*d+„ Z$d,d-„ Z%d.d/„ Z&d0d1„ Z'd2d3„ Z(d4S )5ÚIntegerRingaÌ  The domain ``ZZ`` representing the integers `\mathbb{Z}`.

    The :py:class:`IntegerRing` class represents the ring of integers as a
    :py:class:`~.Domain` in the domain system. :py:class:`IntegerRing` is a
    super class of :py:class:`PythonIntegerRing` and
    :py:class:`GMPYIntegerRing` one of which will be the implementation for
    :ref:`ZZ` depending on whether or not ``gmpy`` or ``gmpy2`` is installed.

    See also
    ========

    Domain
    ÚZZr   é   Tc                 C   s   dS )z$Allow instantiation of this domain. N© )Úselfr   r   úo/Users/vegardjervell/Documents/master/model/venv/lib/python3.9/site-packages/sympy/polys/domains/integerring.pyÚ__init__2   s    zIntegerRing.__init__c                 C   s   t t|ƒƒS )z!Convert ``a`` to a SymPy object. )r   Úint©r   Úar   r   r   Úto_sympy5   s    zIntegerRing.to_sympyc                 C   s>   |j rt|jƒS |jr.t|ƒ|kr.tt|ƒƒS td| ƒ‚dS )z&Convert SymPy's Integer to ``dtype``. zexpected an integer, got %sN)Z
is_Integerr   ÚpZis_Floatr   r   r   r   r   r   Ú
from_sympy9   s
    
zIntegerRing.from_sympyc                 C   s   ddl m} |S )as  Return the associated field of fractions :ref:`QQ`

        Returns
        =======

        :ref:`QQ`:
            The associated field of fractions :ref:`QQ`, a
            :py:class:`~.Domain` representing the rational numbers
            `\mathbb{Q}`.

        Examples
        ========

        >>> from sympy import ZZ
        >>> ZZ.get_field()
        QQ
        r   )ÚQQ)Zsympy.polys.domainsr   )r   r   r   r   r   Ú	get_fieldB   s    zIntegerRing.get_fieldc                 G   s   |   ¡ j|Ž S )a)  Returns an algebraic field, i.e. `\mathbb{Q}(\alpha, \ldots)`.

        Parameters
        ==========

        *extension: One or more Expr.
            Generators of the extension. These should be expressions that are
            algebraic over `\mathbb{Q}`.

        Returns
        =======

        :py:class:`~.AlgebraicField`
            A :py:class:`~.Domain` representing the algebraic field extension.

        Examples
        ========

        >>> from sympy import ZZ, sqrt
        >>> ZZ.algebraic_field(sqrt(2))
        QQ<sqrt(2)>
        )r   Úalgebraic_field)r   Ú	extensionr   r   r   r   W   s    zIntegerRing.algebraic_fieldc                 C   s   |j r|  | ¡ |j¡S dS )zcConvert a :py:class:`~.ANP` object to :ref:`ZZ`.

        See :py:meth:`~.Domain.convert`.
        N)Z	is_groundÚconvertZLCÚdom©ÚK1r   ÚK0r   r   r   Úfrom_AlgebraicFieldp   s    zIntegerRing.from_AlgebraicFieldc                 C   s   |   t t|ƒ|¡¡S )a)  logarithm of *a* to the base *b*

        Parameters
        ==========

        a: number
        b: number

        Returns
        =======

        $\\lfloor\log(a, b)\\rfloor$:
            Floor of the logarithm of *a* to the base *b*

        Examples
        ========

        >>> from sympy import ZZ
        >>> ZZ.log(ZZ(8), ZZ(2))
        3
        >>> ZZ.log(ZZ(9), ZZ(2))
        3

        Notes
        =====

        This function uses ``math.log`` which is based on ``float`` so it will
        fail for large integer arguments.
        )ÚdtypeÚmathÚlogr   ©r   r   Úbr   r   r   r(   x   s    zIntegerRing.logc                 C   s   t | ¡ ƒS ©z3Convert ``ModularInteger(int)`` to GMPY's ``mpz``. ©r   Úto_intr"   r   r   r   Úfrom_FF˜   s    zIntegerRing.from_FFc                 C   s   t | ¡ ƒS r+   r,   r"   r   r   r   Úfrom_FF_pythonœ   s    zIntegerRing.from_FF_pythonc                 C   s   t |ƒS ©z,Convert Python's ``int`` to GMPY's ``mpz``. ©r   r"   r   r   r   Úfrom_ZZ    s    zIntegerRing.from_ZZc                 C   s   t |ƒS r0   r1   r"   r   r   r   Úfrom_ZZ_python¤   s    zIntegerRing.from_ZZ_pythonc                 C   s   |j dkrt|jƒS dS ©z1Convert Python's ``Fraction`` to GMPY's ``mpz``. r   N©Údenominatorr   Ú	numeratorr"   r   r   r   Úfrom_QQ¨   s    
zIntegerRing.from_QQc                 C   s   |j dkrt|jƒS dS r4   r5   r"   r   r   r   Úfrom_QQ_python­   s    
zIntegerRing.from_QQ_pythonc                 C   s   |  ¡ S )z3Convert ``ModularInteger(mpz)`` to GMPY's ``mpz``. )r-   r"   r   r   r   Úfrom_FF_gmpy²   s    zIntegerRing.from_FF_gmpyc                 C   s   |S )z*Convert GMPY's ``mpz`` to GMPY's ``mpz``. r   r"   r   r   r   Úfrom_ZZ_gmpy¶   s    zIntegerRing.from_ZZ_gmpyc                 C   s   |j dkr|jS dS )z(Convert GMPY ``mpq`` to GMPY's ``mpz``. r   N)r6   r7   r"   r   r   r   Úfrom_QQ_gmpyº   s    
zIntegerRing.from_QQ_gmpyc                 C   s"   |  |¡\}}|dkrt|ƒS dS )z,Convert mpmath's ``mpf`` to GMPY's ``mpz``. r   N)Zto_rationalr   )r#   r   r$   r   Úqr   r   r   Úfrom_RealField¿   s    zIntegerRing.from_RealFieldc                 C   s   |j dkr|jS d S )Nr   )ÚyÚxr"   r   r   r   Úfrom_GaussianIntegerRingÆ   s    
z$IntegerRing.from_GaussianIntegerRingc                 C   s,   t ||ƒ\}}}tr|||fS |||fS dS )z)Compute extended GCD of ``a`` and ``b``. N)r   r   )r   r   r*   ÚhÚsÚtr   r   r   r   Ê   s    
zIntegerRing.gcdexc                 C   s
   t ||ƒS )z Compute GCD of ``a`` and ``b``. )r   r)   r   r   r   r   Ò   s    zIntegerRing.gcdc                 C   s
   t ||ƒS )z Compute LCM of ``a`` and ``b``. )r   r)   r   r   r   r   Ö   s    zIntegerRing.lcmc                 C   s   t |ƒS )zCompute square root of ``a``. )r	   r   r   r   r   r	   Ú   s    zIntegerRing.sqrtc                 C   s   t |ƒS )zCompute factorial of ``a``. )r   r   r   r   r   r   Þ   s    zIntegerRing.factorialN))Ú__name__Ú
__module__Ú__qualname__Ú__doc__ÚrepÚaliasr   r&   ZzeroZoneÚtypeÚtpZis_IntegerRingZis_ZZZis_NumericalZis_PIDZhas_assoc_RingZhas_assoc_Fieldr   r   r   r   r   r%   r(   r.   r/   r2   r3   r8   r9   r:   r;   r<   r>   rA   r   r   r   r	   r   r   r   r   r   r      sF   	 r   )rH   Zsympy.external.gmpyr   r   Zsympy.polys.domains.groundtypesr   r   r   r   r   r	   Z&sympy.polys.domains.characteristiczeror
   Zsympy.polys.domains.ringr   Z sympy.polys.domains.simpledomainr   Zsympy.polys.polyerrorsr   Zsympy.utilitiesr   r'   r   r   r   r   r   r   Ú<module>   s     P