B
    ed/                 @   s   d dl mZ d dlmZ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mZ d dlmZmZ d dlmZ d d	lmZmZ d d
lmZ d dlmZ d dlm Z  d dl!m"Z"m#Z# ddl$m$Z$ dddZ%dd Z&G dd deZ'dS )    )AccumBounds)SSymbolAddsympifyExpr	PoleErrorMul)factor_terms)Float)	factorial)Abssign)explog)gamma)PolynomialErrorfactor)Order)powsimp)ratsimp)	nsimplifytogether   )gruntz+c             C   s   t | |||jddS )aQ  Computes the limit of ``e(z)`` at the point ``z0``.

    Parameters
    ==========

    e : expression, the limit of which is to be taken

    z : symbol representing the variable in the limit.
        Other symbols are treated as constants. Multivariate limits
        are not supported.

    z0 : the value toward which ``z`` tends. Can be any expression,
        including ``oo`` and ``-oo``.

    dir : string, optional (default: "+")
        The limit is bi-directional if ``dir="+-"``, from the right
        (z->z0+) if ``dir="+"``, and from the left (z->z0-) if
        ``dir="-"``. For infinite ``z0`` (``oo`` or ``-oo``), the ``dir``
        argument is determined from the direction of the infinity
        (i.e., ``dir="-"`` for ``oo``).

    Examples
    ========

    >>> from sympy import limit, sin, oo
    >>> from sympy.abc import x
    >>> limit(sin(x)/x, x, 0)
    1
    >>> limit(1/x, x, 0) # default dir='+'
    oo
    >>> limit(1/x, x, 0, dir="-")
    -oo
    >>> limit(1/x, x, 0, dir='+-')
    zoo
    >>> limit(1/x, x, oo)
    0

    Notes
    =====

    First we try some heuristics for easy and frequent cases like "x", "1/x",
    "x**2" and similar, so that it's fast. For all other cases, we use the
    Gruntz algorithm (see the gruntz() function).

    See Also
    ========

     limit_seq : returns the limit of a sequence.
    F)deep)Limitdoit)ezz0dir r#   `/work/yifan.wang/ringdown/master-ringdown-env/lib/python3.7/site-packages/sympy/series/limits.pylimit   s    3r%   c             C   s8  d}t |tjkrNt| |d| |tj|tjkr6dnd}t|trJdS n| jsh| j	sh| j
sh| jr4g }x| jD ]}t||||}|tjr|jdkrt| trt| }t|tst|}t|tst| }t|trt||||S dS dS t|trdS |tjkrdS || qtW |r4| j| }|tjkr| jrtdd |D rg }	g }
xFtt|D ]6}t|| tr|	||  n|
| j|  qnW t|
dkrt|
  }t||||}|t|	  }|tjkr4yt| }W n tk
r
   dS X |tjks"|| kr&dS t||||S |S )a+  Computes the limit of an expression term-wise.
    Parameters are the same as for the ``limit`` function.
    Works with the arguments of expression ``e`` one by one, computing
    the limit of each and then combining the results. This approach
    works only for simple limits, but it is fast.
    Nr   r   -c             s   s   | ]}t |tV  qd S )N)
isinstancer   ).0rrr#   r#   r$   	<genexpr>j   s    zheuristics.<locals>.<genexpr>r   )absr   Infinityr%   subsZeror'   r   is_MulZis_Addis_PowZis_Functionargshas	is_finiter   r
   r	   r   r   
heuristicsNaNappendfuncanyrangelenr   simplifyr   r   )r   r    r!   r"   rvralmr2e2iiZe3Zrat_er#   r#   r$   r4   F   s^    *





(r4   c               @   s6   e Zd ZdZdddZedd Zdd Zd	d
 ZdS )r   zRepresents an unevaluated limit.

    Examples
    ========

    >>> from sympy import Limit, sin
    >>> from sympy.abc import x
    >>> Limit(sin(x)/x, x, 0)
    Limit(sin(x)/x, x, 0)
    >>> Limit(1/x, x, 0, dir="-")
    Limit(1/x, x, 0, dir='-')

    r   c             C   s   t |}t |}t |}|tjkr(d}n|tjkr6d}||rPtd||f t|trdt|}nt|ts~t	dt
| t|dkrtd| t| }||||f|_|S )Nr&   r   z@Limits approaching a variable point are not supported (%s -> %s)z6direction must be of type basestring or Symbol, not %s)r   r&   z+-z1direction must be one of '+', '-' or '+-', not %s)r   r   r,   NegativeInfinityr2   NotImplementedErrorr'   strr   	TypeErrortype
ValueErrorr   __new___args)clsr   r    r!   r"   objr#   r#   r$   rJ      s*    






zLimit.__new__c             C   s8   | j d }|j}|| j d j || j d j |S )Nr   r      )r1   free_symbolsdifference_updateupdate)selfr   Zisymsr#   r#   r$   rO      s
    
zLimit.free_symbolsc       
      C   s   | j \}}}}|j|j }}||sBt|t| ||}t|S t|||}t|||}	|	tjkr|tjtj	fkrt||d  ||}t|S |	tj	kr|tjkrtj
S d S )Nr   )r1   baser   r2   r%   r   r   Oner,   rD   ComplexInfinity)
rR   r   _r    r!   b1e1resZex_limZbase_limr#   r#   r$   pow_heuristics   s    

zLimit.pow_heuristicsc       	   
      s4  | j \} tjkr td|ddrP|jf |}jf |jf ||kr\S |sj|S tjkrztjS |tjtj	tjtjr| S |j
rtt|jf|j dd  S d}t dkrd}nt dkrd	} fd
d|tr
t|}|}|rttjkrH|d }| }n| }y|j|d\}}W n tk
r   Y ndX |dkrtjS |dkr|S |dkst|d@ stjt| S |d	krtj	t| S tjS ttjkr |jrt|}|d }| }n| }y|j|d\}}W nD tttfk
r   t|}|jr| |}|dk	r|S Y nX |tjtj	tjr| S |s^|jrtjS |dkr|S |j r^|j!r|dks|j"rtjt| S |d	krtj	t| S tjS n@|dkr6tjt| S |d	krXtjt| tj#|  S tjS j$rr|%t&t'}d}yvt dkrt(|d}t(|d}||krtd||f nt(| }|tjks|tjkrt W nB ttfk
r.   |dk	r t)| }|dkr*| S Y nX |S )aP  Evaluates the limit.

        Parameters
        ==========

        deep : bool, optional (default: True)
            Invoke the ``doit`` method of the expressions involved before
            taking the limit.

        hints : optional keyword arguments
            To be passed to ``doit`` methods; only used if deep is True.
        z.Limits at complex infinity are not implementedr   Tr   Nr   r   r&   c                s   | j s
| S tfdd| j D }|| j kr6| j| } t| t}t| t}|sR|rt| j d  }|jrtd| j d   }|jr|dk dkr|r| j d  S t	j
S |dkdkr|r| j d S t	jS | S )Nc             3   s   | ]} |V  qd S )Nr#   )r(   arg)	set_signsr#   r$   r*      s    z0Limit.doit.<locals>.set_signs.<locals>.<genexpr>r   r   T)r1   tupler7   r'   r   r   r%   is_zeroZis_extended_realr   NegativeOnerT   )exprZnewargsZabs_flagZ	sign_flagsig)r"   r]   r    r!   r#   r$   r]      s"    



zLimit.doit.<locals>.set_signs)cdirz+-zMThe limit does not exist since left hand limit = %s and right hand limit = %s)*r1   r   rU   rE   getr   r2   r5   r,   rD   Zis_Orderr   r%   ra   rF   r   r   Zis_meromorphicr+   r-   ZleadtermrI   r.   intr   r/   r
   r   r   r0   rZ   Zis_positiveZis_negative
is_integerZis_evenr`   Zis_extended_positiveZrewriter   r   r   r4   )	rR   hintsr   rc   ZneweZcoeffexr=   r?   r#   )r"   r]   r    r!   r$   r      s    


"














z
Limit.doitN)r   )	__name__
__module____qualname____doc__rJ   propertyrO   rZ   r   r#   r#   r#   r$   r      s
   
	r   N)r   )(Z!sympy.calculus.accumulationboundsr   Z
sympy.corer   r   r   r   r   r   r	   Zsympy.core.exprtoolsr
   Zsympy.core.numbersr   Z(sympy.functions.combinatorial.factorialsr   Z$sympy.functions.elementary.complexesr   r   Z&sympy.functions.elementary.exponentialr   r   Z'sympy.functions.special.gamma_functionsr   Zsympy.polysr   r   Zsympy.series.orderr   Zsympy.simplify.powsimpr   Zsympy.simplify.ratsimpr   Zsympy.simplify.simplifyr   r   r   r%   r4   r   r#   r#   r#   r$   <module>   s    $
6=