B
    [c                 @   s  d Z ddlmZmZ ddlmZ ddl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 dd
lmZ ddl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%m&Z&m'Z' ddl(m)Z) ddl*m+Z+m,Z,m-Z- ddl.m/Z/m0Z0 ddl1m2Z2 ddl3m4Z4 ddl5m6Z6 ddl7m8Z8 dOddZ9dd Z:dPddZ;d d! Z<d"d# Z=d$d% Z>d&d' Z?d(d) Z@d*d+ ZAd,d- ZBd.d/ ZCd0d1 ZDd2d3 ZEd4d5 ZFd6d7 ZGd8d9 ZHd:d; ZId<d= ZJd>d? ZKd@dA ZLdQdBdCZMdDdE ZNdRdHdIZOG dJdK dKe4ZPdSdMdNZQdLS )TzFormal Power Series    )print_functiondivision)defaultdict)oozoonan)Expr)Add)Mul)
DerivativeFunction)S)sympify)WildDummysymbolsSymbol)Eq)Rational)iterable)Interval)binomial	factorialrf)	Piecewise)floorfracceiling)MinMax)sequence)
SeriesBase)Order)Limit   Fc             C   s  ddl m}m} ddlm} | }g }	xt|d D ]}
|
rH||}||rtj	tj	 }}||||d}|
|r| }xt|D ]}| \}}|
|s||7 }qt|tr||}|d }||d  }| \}}||\}}|s||7 }q|d |}||  }|||  }d| | t|| d |t |||   }||7 }qW |tj	krtdS |
|s|
ts|
ts|
trdS xDt|
D ]8}||| d  }|||}||	 | |d7 }qW ||||
 ||
fS |	| q4W dS )a?  Rational algorithm for computing
    formula of coefficients of Formal Power Series
    of a function.

    Applicable when f(x) or some derivative of f(x)
    is a rational function in x.

    :func:`rational_algorithm` uses :func:`apart` function for partial fraction
    decomposition. :func:`apart` by default uses 'undetermined coefficients
    method'. By setting ``full=True``, 'Bronstein's algorithm' can be used
    instead.

    Looks for derivative of a function up to 4'th order (by default).
    This can be overridden using order option.

    Returns
    =======

    formula : Expr
    ind : Expr
        Independent terms.
    order : int

    Examples
    ========

    >>> from sympy import log, atan, I
    >>> from sympy.series.formal import rational_algorithm as ra
    >>> from sympy.abc import x, k

    >>> ra(1 / (1 - x), x, k)
    (1, 0, 0)
    >>> ra(log(1 + x), x, k)
    (-(-1)**(-k)/k, 0, 1)

    >>> ra(atan(x), x, k, full=True)
    ((-I*(-I)**(-k)/2 + I*I**(-k)/2)/k, 0, 1)

    Notes
    =====

    By setting ``full=True``, range of admissible functions to be solved using
    ``rational_algorithm`` can be increased. This option should be used
    carefully as it can significantly slow down the computation as ``doit`` is
    performed on the :class:`RootSum` object returned by the ``apart`` function.
    Use ``full=False`` whenever possible.

    See Also
    ========

    sympy.polys.partfrac.apart

    References
    ==========

    .. [1] Formal Power Series - Dominik Gruntz, Wolfram Koepf
    .. [2] Power Series in Computer Algebra - Wolfram Koepf
    r   )RootSumapart)	integrate   )fullN)sympy.polysr%   r&   sympy.integralsr'   rangediffis_rational_functionr   ZerohasZdoitr	   	make_argsas_numer_denom
isinstancer
   as_independentas_base_expZas_coeff_addcoeffr   Zrewriter   r   r   r   poplimitsubsappend)fxkorderr)   r%   r&   r'   r.   Zdsir7   septermstZnumZdenindjaxtermZxcak rI   2lib/python3.7/site-packages/sympy/series/formal.pyrational_algorithm   sV    ;






"$
rK   c       	      C   s   | sg S | dd }xx| dd D ]h}| |d }xTt|D ]>\}}| |d }||  }||r>||  |7  < P q>W || q"W |S )a  Returns a list of all the rationally independent terms.

    Examples
    ========

    >>> from sympy import sin, cos
    >>> from sympy.series.formal import rational_independent
    >>> from sympy.abc import x

    >>> rational_independent([cos(x), sin(x)], x)
    [cos(x), sin(x)]
    >>> rational_independent([x**2, sin(x), x*sin(x), x**3], x)
    [x**3 + x**2, x*sin(x) + sin(x)]
    r   r(   N)r5   	enumerateZcancelr/   r;   )	rB   r=   rD   rC   nr@   termdqrI   rI   rJ   rational_independent   s    
rQ   c          
   #   s   ddl m} td|   fdd}||\}}d}xtd|d D ]}	||	\}}| }| }
t|
}|st||	krJtt	 dd	 || d
|	 D }|rd}|
|}| d }| td d }|t|	fV  qJW d
S )a^  Generates simple DE.

    DE is of the form

    .. math::
        f^k(x) + \sum\limits_{j=0}^{k-1} A_j f^j(x) = 0

    where :math:`A_j` should be rational function in x.

    Generates DE's upto order 4 (default). DE's can also have free parameters.

    By increasing order, higher order DE's can be found.

    Yields a tuple of (DE, order).
    r   )linsolveza:%dc                sd    | t fddtd| D   } | t fddtd| D   }||fS )Nc                s    g | ]} |  | qS rI   )r.   ).0r@   )rF   r<   r=   rI   rJ   
<listcomp>   s    z-simpleDE.<locals>._makeDE.<locals>.<listcomp>r   c                s$   g | ]} |  | qS rI   )r.   )rS   r@   )rF   gr=   rI   rJ   rT      s    )r.   r	   r-   )r>   eqDE)rF   r<   rU   r=   rI   rJ   _makeDE   s    ,0zsimpleDE.<locals>._makeDEFr(   c             s   s   | ]}|D ]
}|V  q
qd S )NrI   )rS   sr@   rI   rI   rJ   	<genexpr>   s    zsimpleDE.<locals>.<genexpr>NT)sympy.solvers.solvesetrR   r   r-   expandZas_ordered_termsrQ   lendictzipr:   r3   factoras_coeff_mulr   collect)r<   r=   rU   r?   rR   rX   rV   rW   foundr>   rB   rD   solrI   )rF   r<   rU   r=   rJ   simpleDE   s$    
&
re   c       
      C   s   t j}| t }d}x^t| D ]P}||\}}t|t	rH|j
}	nd}	|dks\|	|k r`|	}|||||	  7 }q$W |r|||| }|S )az  Converts a DE with constant coefficients (explike) into a RE.

    Performs the substitution:

    .. math::
        f^j(x) \to r(k + j)

    Normalises the terms so that lowest order of a term is always r(k).

    Examples
    ========

    >>> from sympy import Function, Derivative
    >>> from sympy.series.formal import exp_re
    >>> from sympy.abc import x, k
    >>> f, r = Function('f'), Function('r')

    >>> exp_re(-f(x) + Derivative(f(x)), r, k)
    -r(k) + r(k + 1)
    >>> exp_re(Derivative(f(x), x) + Derivative(f(x), (x, 2)), r, k)
    r(k) + r(k + 1)

    See Also
    ========

    sympy.series.formal.hyper_re
    Nr   )r   r0   atomsr   r8   r	   r2   r5   r4   r   derivative_countr:   )
rW   rr>   RErU   minirC   r7   rO   rE   rI   rI   rJ   exp_re   s    
rk   c             C   s   t j}| t }|t }d}xt|  D ]}|	|\}}	|	|\}
}|
|d }t|	trv|	j}nd}||
t|d | | ||| |  7 }|dks|| |k r6|| }q6W |||| }td}|||| S )a}  Converts a DE into a RE.

    Performs the substitution:

    .. math::
        x^l f^j(x) \to (k + 1 - l)_j . a_{k + j - l}

    Normalises the terms so that lowest order of a term is always r(k).

    Examples
    ========

    >>> from sympy import Function, Derivative
    >>> from sympy.series.formal import hyper_re
    >>> from sympy.abc import x, k
    >>> f, r = Function('f'), Function('r')

    >>> hyper_re(-f(x) + Derivative(f(x)), r, k)
    (k + 1)*r(k + 1) - r(k)
    >>> hyper_re(-x*f(x) + Derivative(f(x), (x, 2)), r, k)
    (k + 2)*(k + 3)*r(k + 3) - r(k)

    See Also
    ========

    sympy.series.formal.exp_re
    Nr(   r   m)r   r0   rf   r   r8   r   r	   r2   r\   r5   Zas_coeff_exponentr4   r   rg   r   r:   r   rb   )rW   rh   r>   ri   rU   r=   rj   rC   r7   rO   cvlrE   rl   rI   rI   rJ   hyper_re  s"    
*rp   c             C   s:   | ||  9 } | ||| }| ||| }| |||fS )N)r:   )r<   r=   PQr>   rl   shiftrI   rI   rJ   _transformation_aH  s    rt   c             C   sD   |  ||| } | ||| }| ||| }||9 }| |||fS )N)r:   )r<   r=   rq   rr   r>   rl   scalerI   rI   rJ   _transformation_cO  s
    rv   c             C   sJ   |  |} |||d || d  }|||d |d  }| |||fS )Nr(   )r.   r:   )r<   r=   rq   rr   r>   rl   rI   rI   rJ   _transformation_eW  s    
rw   c                s    fdd| D S )Nc                s   g | ]\}}||  fqS rI   rI   )rS   rescond)rs   rI   rJ   rT   _  s    z _apply_shift.<locals>.<listcomp>rI   )rd   rs   rI   )rs   rJ   _apply_shift^  s    rz   c                s    fdd| D S )Nc                s   g | ]\}}||  fqS rI   rI   )rS   rx   ry   )ru   rI   rJ   rT   c  s    z _apply_scale.<locals>.<listcomp>rI   )rd   ru   rI   )ru   rJ   _apply_scaleb  s    r{   c                s    fdd| D S )Nc                s6   g | ].\}}||d  |  d     |d  fqS )r(   )as_coeff_Addr7   )rS   rx   ry   )r>   rI   rJ   rT   g  s   z$_apply_integrate.<locals>.<listcomp>rI   )rd   r=   r>   rI   )r>   rJ   _apply_integratef  s    
r}   c             C   s>  ddl m} g }x&t|d || d D ]
}	| ||	|dt|	 }
|
tjkrXq*|| |	 }|
}|||}|||}||d| 	|d }||d| 	|d }|| | | 9 }x.|||
 D ]\}
}|t|
 || 9 }qW x0|||
 D ]\}
}|t|
 ||  }qW |||f q*W |S )zComputes the formula for f.r   )rootsr(   )r+   r~   r-   r.   r9   r   r   r0   r:   Zleadtermitemsr   r;   )r<   r=   rq   rr   r>   rl   k_maxr~   rd   r@   rh   Zktermrx   prP   Zc1Zc2mulrI   rI   rJ   _compute_formulak  s&     
r   c          	   C   sn  ddl m}m} ddlm} |||||| }	}
t|	}||
 |dd | D }t| ||||||\} }}}|||}
|
rt	|

  }ntj}|| }t| ||||||\} }}}||  |d}t|ts|dkrdS |||}
|
r t|

  }ntj}tjt  }}xt|| d D ]}| |||dt| }|jdkr| }t| ||||||\} }}}t| |||||\} }}}t| |||||\}}}t|||}t||}|||}||| |d7 }|d7 }|||fS |r(|||||   7 }t|| |}||kr(|}q(W |||d|  }t| ||||||}t||}t||}|||fS )	zRecursive wrapper to rsolve_hypergeometric.

    Returns a Tuple of (formula, series independent terms,
    maximum power of x in independent terms) if successful
    otherwise ``None``.

    See :func:`rsolve_hypergeometric` for details.
    r   )lcmr~   )r'   c             S   s"   g | ]\}}|j r| d  qS )r(   )Zis_rationalr3   )rS   rh   rC   rI   rI   rJ   rT     s    z*_rsolve_hypergeometric.<locals>.<listcomp>Nr(   F)r+   r   r~   r,   r'   r^   updater   rv   r   keysr   r0   rt   r9   r4   r#   r   r   r-   r.   r   Z	is_finiterw   _rsolve_hypergeometricr}   rz   r   r:   r   r{   )r<   r=   rq   rr   r>   rl   r   r~   r'   ZprootsZqrootsZ	all_rootsru   Zk_minrs   ro   r   rD   mpr@   rh   Zold_frd   pow_xrI   rI   rJ   r     sX    	









r   c             C   s`  t | |||||}|dkrdS |\}}}	tdd }
x~|D ]v\}}| \}}||}|jdkrz||t| 9 }t|}|||| | }t|| || }|
|  |7  < q:W g }x"|
	 D ]\}}|
||f qW |
tjdf t| }|	t krtj}n|	jdkrt|	}n|	d }|dk rV|tt|||  ||df7 }tj}|||fS )	a  Solves RE of hypergeometric type.

    Attempts to solve RE of the form

    Q(k)*a(k + m) - P(k)*a(k)

    Transformations that preserve Hypergeometric type:

        a. x**n*f(x): b(k + m) = R(k - n)*b(k)
        b. f(A*x): b(k + m) = A**m*R(k)*b(k)
        c. f(x**n): b(k + n*m) = R(k/n)*b(k)
        d. f(x**(1/m)): b(k + 1) = R(k*m)*b(k)
        e. f'(x): b(k + m) = ((k + m + 1)/(k + 1))*R(k + 1)*b(k)

    Some of these transformations have been used to solve the RE.

    Returns
    =======

    formula : Expr
    ind : Expr
        Independent terms.
    order : int

    Examples
    ========

    >>> from sympy import exp, ln, S
    >>> from sympy.series.formal import rsolve_hypergeometric as rh
    >>> from sympy.abc import x, k

    >>> rh(exp(x), x, -S.One, (k + 1), k, 1)
    (Piecewise((1/factorial(k), Eq(Mod(k, 1), 0)), (0, True)), 1, 1)

    >>> rh(ln(1 + x), x, k**2, k*(k + 1), k, 1)
    (Piecewise(((-1)**(k - 1)*factorial(k - 1)/RisingFactorial(2, k - 1),
     Eq(Mod(k, 1), 0)), (0, True)), x, 2)

    References
    ==========

    .. [1] Formal Power Series - Dominik Gruntz, Wolfram Koepf
    .. [2] Power Series in Computer Algebra - Wolfram Koepf
    Nc               S   s   t jS )N)r   r0   rI   rI   rI   rJ   <lambda>  s    z'rsolve_hypergeometric.<locals>.<lambda>FTr(   r   r*   )r   r   r|   r7   
is_integerr   r   r:   r   r   r;   r   r0   r   r   r   sumr    )r<   r=   rq   rr   r>   rl   resultZsol_listrD   r   Zsol_dictrx   ry   rE   Zmkrm   rd   rY   rI   rI   rJ   rsolve_hypergeometric  s8    -




 r   c       
      C   s   t |}t|dkr|t|t}t|j|\}}|d jd |d jd  }	|	dk rj|| }}t	|	}	t
| |||||	S dS )z;See docstring of :func:`rsolve_hypergeometric` for details.   r(   r   N)r	   r2   r]   listrf   r   mapr7   argsabsr   )
r<   r=   ri   rU   r>   rB   Zgsrq   rr   rl   rI   rI   rJ   _solve_hyper_RE"  s    

r   c             C   s   ddl m} x*t|D ]}||\}}|jrdS qW t|||}	i }
xDttt|	D ].}|rn| 	|} | 
|d|
||||< q\W ||	|||
}|r|t| tjtjfS dS )z%Solves DE with constant coefficients.r   )rsolveN)sympy.solversr   r	   r2   r5   free_symbolsrk   r-   r]   r.   r9   r:   r   r   r0   )r<   r=   rW   rU   r>   r   rC   r7   rO   ri   initr@   rd   rI   rI   rJ   _solve_explike_DE0  s    
 r   c       
      C   s   ddl m} t|||}i }xLttt|D ]6}|rB| |} | |dt	| |||
||< q0W |||||}	|	r|	tjtjfS dS )z4Converts DE into RE and solves using :func:`rsolve`.r   )r   N)r   r   rp   r-   r]   r	   r2   r.   r9   r   r:   r   r0   )
r<   r=   rW   rU   r>   r   ri   r   r@   rd   rI   rI   rJ   _solve_simpleG  s    
(r   c             C   s  ddl m} g }| t||||}xVt|D ]J}| t||||}	|	|  |}	xt|	D ]}
|	|
 qhW q0W g }x2|D ]&}|
|rP q|
tr|	| qW |}|rtt|dd ||t|D }|r| |} |  td d } | t||} | S )zDConverts DE with free parameters into DE with constant coefficients.r   )rR   c             s   s   | ]}|D ]
}|V  q
qd S )NrI   )rS   rY   r@   rI   rI   rJ   rZ   m  s    z(_transform_explike_DE.<locals>.<genexpr>r(   )r[   rR   r7   r   r-   r\   rb   r	   r2   r;   r1   r   r^   r_   r   r:   r`   ra   )rW   rU   r=   r?   symsrR   rV   Zhighest_coeffr@   r7   rC   temperd   rI   rI   rJ   _transform_explike_DEY  s,    


"
r   c             C   s   ddl m} t| ||}g }x.td|D ] }|||| }	||	 q(W tt|dd ||t|D }
|
rt	d}|
|
}|  d ||| }||d d }x8t|D ],}|||| r|r|
||| }P qW |S )z@Converts DE with free parameters into RE of hypergeometric type.r   )rR   r(   c             s   s   | ]}|D ]
}|V  q
qd S )NrI   )rS   rY   r@   rI   rI   rJ   rZ     s    z#_transform_DE_RE.<locals>.<genexpr>rl   )r[   rR   rp   r-   r7   r;   r^   r_   r   r   r:   r`   r3   rb   ra   )rW   rU   r>   r?   r   rR   ri   rV   r@   r7   rd   rl   rI   rI   rJ   _transform_DE_REu  s"    "
r   c       	      C   s   d}|j ||h}|r*t|||||}nt|||}|j |hsTt| ||||}|r\|S |rpt|||||}|j |hst| ||||}|r|S dS )a  Solves the DE.

    Tries to solve DE by either converting into a RE containing two terms or
    converting into a DE having constant coefficients.

    Returns
    =======

    formula : Expr
    ind : Expr
        Independent terms.
    order : int

    Examples
    ========

    >>> from sympy import Derivative as D, Function
    >>> from sympy import exp, ln
    >>> from sympy.series.formal import solve_de
    >>> from sympy.abc import x, k
    >>> f = Function('f')

    >>> solve_de(exp(x), x, D(f(x), x) - f(x), 1, f, k)
    (Piecewise((1/factorial(k), Eq(Mod(k, 1), 0)), (0, True)), 1, 1)

    >>> solve_de(ln(1 + x), x, (x + 1)*D(f(x), x, 2) + D(f(x)), 2, f, k)
    (Piecewise(((-1)**(k - 1)*factorial(k - 1)/RisingFactorial(2, k - 1),
     Eq(Mod(k, 1), 0)), (0, True)), x, 2)
    N)r   
differencer   rp   r   r   r   )	r<   r=   rW   r?   rU   r>   rd   r   ri   rI   rI   rJ   solve_de  s    r   c       	      C   s   t d}g }d}xTt| |||D ]B\}}|dk	rBt| |||||}|rJ|S |j|hs || q W x$|D ]}t| ||||}|rl|S qlW dS )a  Hypergeometric algorithm for computing Formal Power Series.

    Steps:
        * Generates DE
        * Convert the DE into RE
        * Solves the RE

    Examples
    ========

    >>> from sympy import exp, ln
    >>> from sympy.series.formal import hyper_algorithm

    >>> from sympy.abc import x, k

    >>> hyper_algorithm(exp(x), x, k)
    (Piecewise((1/factorial(k), Eq(Mod(k, 1), 0)), (0, True)), 1, 1)

    >>> hyper_algorithm(ln(1 + x), x, k)
    (Piecewise(((-1)**(k - 1)*factorial(k - 1)/RisingFactorial(2, k - 1),
     Eq(Mod(k, 1), 0)), (0, True)), x, 2)

    See Also
    ========

    sympy.series.formal.simpleDE
    sympy.series.formal.solve_de
    rU   N)r   re   r   r   r   r;   r   )	r<   r=   r>   r?   rU   Zdesrd   rW   r@   rI   rI   rJ   hyper_algorithm  s    
r   c          
   C   s  |t jt j gkr|t jkr"t jnt j }| |d| }t||d|||||}	|	dkr\dS |	d |	d |d| |	d |d| fS |s|t j kr0|t j kr| | }
| }|}n|| }
|}| }| ||
}t||dt j||||}	|	dkrdS |	d |	d ||| |	d ||| fS | |r@dS t| tr\d}	tt j	dt
f}t j	d }}xt| D ]}t||dt j||||}|r:|	sd}	|d }|d j|jkr|}|j|d j }} n|d }|d j|j }} tdd t|d| |  |||  D  }||d 7 }||d | 7 }n||7 }qxW |	rX|||fS dS d}	td	}|r~t| ||||}	|	dkr|rt| |||}	|	dkrdS t|	d ||	d t
f}t|| |dt
f}|	d }|||fS )
zPRecursive wrapper to compute fps.

    See :func:`compute_fps` for details.
    r(   r   Nr   FTc             S   s   g | ]}|d  |d  qS )r   r(   rI   )rS   zrI   rI   rJ   rT   $  s    z _compute_fps.<locals>.<listcomp>r>   )r   InfinityOner:   _compute_fpsZis_polynomialr4   r	   r    r0   r   r2   startr_   r   rK   r   )r<   r=   x0dirhyperr?   rationalr)   r   r   ZrepZrep2Zrep2brH   rD   xkrC   rx   seqrY   saver>   rI   rI   rJ   r     sr    .

,

r   r(   Tc          	   C   s   t | } t |}| |sdS t |}|dkr6tj}n6|dkrHtj }n$|tjtj gkrdtdnt |}t| |||||||S )a  Computes the formula for Formal Power Series of a function.

    Tries to compute the formula by applying the following techniques
    (in order):

    * rational_algorithm
    * Hypergeomitric algorithm

    Parameters
    ==========

    x : Symbol
    x0 : number, optional
        Point to perform series expansion about. Default is 0.
    dir : {1, -1, '+', '-'}, optional
        If dir is 1 or '+' the series is calculated from the right and
        for -1 or '-' the series is calculated from the left. For smooth
        functions this flag will not alter the results. Default is 1.
    hyper : {True, False}, optional
        Set hyper to False to skip the hypergeometric algorithm.
        By default it is set to False.
    order : int, optional
        Order of the derivative of ``f``, Default is 4.
    rational : {True, False}, optional
        Set rational to False to skip rational algorithm. By default it is set
        to True.
    full : {True, False}, optional
        Set full to True to increase the range of rational algorithm.
        See :func:`rational_algorithm` for details. By default it is set to
        False.

    Returns
    =======

    ak : sequence
        Sequence of coefficients.
    xk : sequence
        Sequence of powers of x.
    ind : Expr
        Independent terms.
    mul : Pow
        Common terms.

    See Also
    ========

    sympy.series.formal.rational_algorithm
    sympy.series.formal.hyper_algorithm
    N+-zDir must be '+' or '-')r   r1   r   r   
ValueErrorr   )r<   r=   r   r   r   r?   r   r)   rI   rI   rJ   compute_fpsA  s    3


r   c               @   s&  e Zd ZdZdd Zedd Zedd Zedd	 Zed
d Z	edd Z
edd Zedd Zedd Zedd Zedd Zedd Zedd Zdd Zd<dd Zd=d!d"Zd#d$ Zd%d& Zd'd( Zd)d* Zd>d,d-Zd.d/ Zd0d1 Zd2d3 Zd4d5 Zd6d7 Zd8d9 Zd:d; Z d+S )?FormalPowerSeriesa  Represents Formal Power Series of a function.

    No computation is performed. This class should only to be used to represent
    a series. No checks are performed.

    For computing a series use :func:`fps`.

    See Also
    ========

    sympy.series.formal.fps
    c             G   s   t t|}tj| f| S )N)r   r   r   __new__)clsr   rI   rI   rJ   r     s    
zFormalPowerSeries.__new__c             C   s
   | j d S )Nr   )r   )selfrI   rI   rJ   function  s    zFormalPowerSeries.functionc             C   s
   | j d S )Nr(   )r   )r   rI   rI   rJ   r=     s    zFormalPowerSeries.xc             C   s
   | j d S )Nr   )r   )r   rI   rI   rJ   r     s    zFormalPowerSeries.x0c             C   s
   | j d S )N   )r   )r   rI   rI   rJ   r     s    zFormalPowerSeries.dirc             C   s   | j d d S )Nr$   r   )r   )r   rI   rI   rJ   rH     s    zFormalPowerSeries.akc             C   s   | j d d S )Nr$   r(   )r   )r   rI   rI   rJ   r     s    zFormalPowerSeries.xkc             C   s   | j d d S )Nr$   r   )r   )r   rI   rI   rJ   rD     s    zFormalPowerSeries.indc             C   s
   t dtS )Nr   )r   r   )r   rI   rI   rJ   interval  s    zFormalPowerSeries.intervalc             C   s   | j jS )N)r   inf)r   rI   rI   rJ   r     s    zFormalPowerSeries.startc             C   s   | j jS )N)r   Zsup)r   rI   rI   rJ   stop  s    zFormalPowerSeries.stopc             C   s   t S )N)r   )r   rI   rI   rJ   length  s    zFormalPowerSeries.lengthc             C   sJ   ddl m} | j| j }}|jd }||j|j ||j|jf}| j| S )z0Returns an infinite representation of the seriesr   )Sum)	Zsympy.concreter   rH   r   	variablesformular   r   rD   )r   r   rH   r   r>   Zinf_sumrI   rI   rJ   infinite  s
    
zFormalPowerSeries.infinitec             C   s.   | | jd  \}}|| js*tjS |S )z!Returns the power of x in a term.r(   )r5   r=   r6   r1   r   r0   )r   rN   rG   r   rI   rI   rJ   
_get_pow_x  s    zFormalPowerSeries._get_pow_x   c             C   sf   g }xXt | D ]L\}}| |}||kr,P q|jdkrF||d krFP q|tjk	r|| qW t| S )zTruncated series as polynomial.

        Returns series sexpansion of ``f`` upto order ``O(x**n)``
        as a polynomial(without ``O`` term).
        Tr(   )rL   r   r   r   r0   r;   r	   )r   rM   rB   r@   rC   ZxprI   rI   rJ   
polynomial  s    

zFormalPowerSeries.polynomialc             C   sR   |dkrt | S | j| j }}| j|}|tjkr:tj}| |t	|||f S )zTruncated series.

        Returns truncated series expansion of f upto
        order ``O(x**n)``.

        If n is ``None``, returns an infinite iterator.
        N)
iterr=   r   r   r7   r   ZNegativeInfinityr   r   r"   )r   rM   r=   r   pt_xkrI   rI   rJ   truncate  s    
zFormalPowerSeries.truncatec             C   s   y | j |}| j| }W n tk
r:   tj}Y n
X || }| jrtj}xTt	| jD ]D}| 
|}|dkr|dk r||7 }q^||kr^||d k r^||7 }q^W ||7 }|| jS )Nr   r(   )r   r7   rH   Zsimplify
IndexErrorr   r0   rD   r	   r2   r   rb   r=   )r   Zptr   Zpt_akrN   rD   rC   r   rI   rI   rJ   
_eval_term  s     

zFormalPowerSeries._eval_termc             C   s   | j }||r| S d S )N)r=   r1   )r   oldnewr=   rI   rI   rJ   
_eval_subs  s    
zFormalPowerSeries._eval_subsc             C   s    x| D ]}|t jk	r|S qW d S )N)r   r0   )r   r=   rC   rI   rI   rJ   _eval_as_leading_term  s    

z'FormalPowerSeries._eval_as_leading_termc          	   C   s  | j |}| j|}| | jj}| j}|jd }|j|rg }xV|jj	D ]J\}}	t
j}
x,t|D ]}| |}|
|||  7 }
qjW ||
|	f qPW t| }t|||d ||jd |jf}n*t|j| ||d ||jd |jf}| || j| j| j|| j|fS )Nr   r(   )r   r.   rD   r   r   r   rH   r   r1   r   r   r0   r	   r2   r;   r   r    r:   r   r   funcr=   r   r   )r   r=   r<   rD   pow_xkrH   r>   formr   rm   r   rC   r   rI   rI   rJ   _eval_derivative  s$    

&z"FormalPowerSeries._eval_derivativeNc          	   K   sd  ddl m} |dkr| j}nt|r0|| j|S || j|}|| j|}||| |d7 }| | jj	}| j
}|jd }|j	|rg }	xZ|j	jD ]N\}
}tj}x0t|
D ]"}| |}|||| d  7 }qW |	||f qW t|	 }	t|	||d ||jd |jf}n.t|j	|d  ||d ||jd |jf}| || j| j| j|| j|fS )aC  Integrate Formal Power Series.

        Examples
        ========

        >>> from sympy import fps, sin, integrate
        >>> from sympy.abc import x
        >>> f = fps(sin(x))
        >>> f.integrate(x).truncate()
        -1 + x**2/2 - x**4/24 + O(x**6)
        >>> integrate(f, (x, 0, 1))
        -cos(1) + 1
        r   )r'   Nr(   )r,   r'   r=   r   r   rD   r9   r   r   r   rH   r   r1   r   r   r0   r	   r2   r;   r   r    r:   r   r   r   r   r   )r   r=   kwargsr'   r<   rD   r   rH   r>   r   r   rm   r   rC   r   rI   rI   rJ   r'   0  s0    

&zFormalPowerSeries.integratec          	   C   sh  t |}t|tr| j|jkr*tdn| j|jkr>td| j|j }}| j|j|| }| j|j	krp|S | j
|j
 }| j
j|j
jkr|j
}|j
j| j
j }}n| j
}| j
j|j
j }}tdd t|d||  | j|| D  }	| j|j |	 }
| ||| j| j|| j|
fS || js^| j| }| j| }
| || j| j| j| j
| j|
fS t| |S )Nz9Both series should be calculated from the same direction.z6Both series should be calculated about the same point.c             S   s   g | ]}|d  |d  qS )r   r(   rI   )rS   r   rI   rI   rJ   rT   t  s    z-FormalPowerSeries.__add__.<locals>.<listcomp>r   )r   r4   r   r   r   r   r=   r   r:   r   rH   r   r	   r_   r   rD   r   r1   )r   otherr=   yr<   rH   r   rY   r   r   rD   rI   rI   rJ   __add__\  s2    
.

zFormalPowerSeries.__add__c             C   s
   |  |S )N)r   )r   r   rI   rI   rJ   __radd__  s    zFormalPowerSeries.__radd__c          	   C   s,   |  | j | j| j| j| j | j| j fS )N)r   r   r=   r   r   rH   r   rD   )r   rI   rI   rJ   __neg__  s    zFormalPowerSeries.__neg__c             C   s   |  | S )N)r   )r   r   rI   rI   rJ   __sub__  s    zFormalPowerSeries.__sub__c             C   s   |   |S )N)r   )r   r   rI   rI   rJ   __rsub__  s    zFormalPowerSeries.__rsub__c          	   C   s^   t |}|| jrt| |S | j| }| j|}| j| }| || j| j	| j
|| j|fS )N)r   r1   r=   r
   r   rH   Z	coeff_mulrD   r   r   r   r   )r   r   r<   rH   rD   rI   rI   rJ   __mul__  s    


zFormalPowerSeries.__mul__c             C   s
   |  |S )N)r   )r   r   rI   rI   rJ   __rmul__  s    zFormalPowerSeries.__rmul__)r   )r   )N)!__name__
__module____qualname____doc__r   propertyr   r=   r   r   rH   r   rD   r   r   r   r   r   r   r   r   r   r   r   r   r'   r   r   r   r   r   r   r   rI   rI   rI   rJ   r     s:   



,&r   Nc       
   	   C   sn   t | } |dkr<| j}t|dkr,| }n|s4| S tdt| |||||||}	|	dkr^| S t| ||||	S )aC  Generates Formal Power Series of f.

    Returns the formal series expansion of ``f`` around ``x = x0``
    with respect to ``x`` in the form of a ``FormalPowerSeries`` object.

    Formal Power Series is represented using an explicit formula
    computed using different algorithms.

    See :func:`compute_fps` for the more details regarding the computation
    of formula.

    Parameters
    ==========

    x : Symbol, optional
        If x is None and ``f`` is univariate, the univariate symbols will be
        supplied, otherwise an error will be raised.
    x0 : number, optional
        Point to perform series expansion about. Default is 0.
    dir : {1, -1, '+', '-'}, optional
        If dir is 1 or '+' the series is calculated from the right and
        for -1 or '-' the series is calculated from the left. For smooth
        functions this flag will not alter the results. Default is 1.
    hyper : {True, False}, optional
        Set hyper to False to skip the hypergeometric algorithm.
        By default it is set to False.
    order : int, optional
        Order of the derivative of ``f``, Default is 4.
    rational : {True, False}, optional
        Set rational to False to skip rational algorithm. By default it is set
        to True.
    full : {True, False}, optional
        Set full to True to increase the range of rational algorithm.
        See :func:`rational_algorithm` for details. By default it is set to
        False.

    Examples
    ========

    >>> from sympy import fps, O, ln, atan
    >>> from sympy.abc import x

    Rational Functions

    >>> fps(ln(1 + x)).truncate()
    x - x**2/2 + x**3/3 - x**4/4 + x**5/5 + O(x**6)

    >>> fps(atan(x), full=True).truncate()
    x - x**3/3 + x**5/5 + O(x**6)

    See Also
    ========

    sympy.series.formal.FormalPowerSeries
    sympy.series.formal.compute_fps
    Nr(   z multivariate formal power series)r   r   r]   r8   NotImplementedErrorr   r   )
r<   r=   r   r   r   r?   r   r)   Zfreer   rI   rI   rJ   fps  s    9
r   )r$   F)r$   )r$   )r   r(   Tr$   TF)Nr   r(   Tr$   TF)Rr   Z
__future__r   r   collectionsr   Zsympyr   r   r   Zsympy.core.exprr   Zsympy.core.addr	   Zsympy.core.mulr
   Zsympy.core.functionr   r   Zsympy.core.singletonr   Zsympy.core.sympifyr   Zsympy.core.symbolr   r   r   r   Zsympy.core.relationalr   Zsympy.core.numbersr   Zsympy.core.compatibilityr   Zsympy.sets.setsr   Z(sympy.functions.combinatorial.factorialsr   r   r   Z$sympy.functions.elementary.piecewiser   Z#sympy.functions.elementary.integersr   r   r   Z(sympy.functions.elementary.miscellaneousr   r   Zsympy.series.sequencesr    Zsympy.series.series_classr!   Zsympy.series.orderr"   Zsympy.series.limitsr#   rK   rQ   re   rk   rp   rt   rv   rw   rz   r{   r}   r   r   r   r   r   r   r   r   r   r   r   r   r   r   rI   rI   rI   rJ   <module>   sd   
|!
+/4CW4
1P 
F  