
    UgL                         d Z ddlZddlmZ ddlmZ dgZg dZ	 G d d	          Z
	 	 	 	 	 ddZd Zd Zd Zd Zd Zd Zd Zd ZdS )z
Unified interfaces to root finding algorithms for real or complex
scalar functions.

Functions
---------
- root : find a root of a scalar function.
    N   )	_zeros_pyapprox_derivativeroot_scalar)bisectbrentqbrenthriddertoms748newtonsecanthalleyc                   0    e Zd ZdZd Zd Zd Zd Zd ZdS )
MemoizeDera  Decorator that caches the value and derivative(s) of function each
    time it is called.

    This is a simplistic memoizer that calls and caches a single value
    of `f(x, *args)`.
    It assumes that `args` does not change between invocations.
    It supports the use case of a root-finder where `args` is fixed,
    `x` changes, and only rarely, if at all, does x assume the same value
    more than once.c                 >    || _         d | _        d | _        d| _        d S )Nr   )funvalsxn_calls)selfr   s     Z/var/www/surfInsights/venv3-11/lib/python3.11/site-packages/scipy/optimize/_root_scalar.py__init__zMemoizeDer.__init__   s"    	    c                     | j         || j        k    r4 | j        |g|R  }|| _        | xj        dz  c_        |dd         | _         | j         d         S )z,Calculate f or use cached value if availableNr   r   )r   r   r   r   )r   r   argsfgs       r   __call__zMemoizeDer.__call__$   sa     9TV!#d###BDFLLALL111DIy|r   c                 R    | j         || j        k    r	 | |g|R   | j         d         S )z/Calculate f' or use a cached value if availableNr   r   r   r   r   r   s      r   fprimezMemoizeDer.fprime.   3    9TVDNTNNNNy|r   c                 R    | j         || j        k    r	 | |g|R   | j         d         S )z0Calculate f'' or use a cached value if availableN   r    r!   s      r   fprime2zMemoizeDer.fprime24   r#   r   c                     | j         S )N)r   )r   s    r   ncallszMemoizeDer.ncalls:   s
    |r   N)	__name__
__module____qualname____doc__r   r   r"   r&   r(    r   r   r   r      si                     r   r   r-   c           	          t          |t                    s|f}|i }d}|@t          |          s1t          |          r t	                      d} j        } j        }nd}|9t          |          s*t          |          rt	                      d} j        }nd}i }dD ]*}t                                          |          }||||<   +|r|	                    |           |	                    dd           |s|rd}n||r|rd}n
d}n|d	}nd}|st          d
          |                                }ddd}	 t          t          |                    ||                    }n%# t          $ r}t          d|z            |d}~ww xY w|dv rt          |t          t          t           j        f          st          d|z            |dd         \  }}	  | ||fd|i|\  }}nx# t          $ rW}t%          |d          r;t          j        |j        t           j        |j        t/          |          |          }n Y d}~nd}~ww xY w|dv rC|t          d|z            d|v r|                    d          |d<    | |f|dd|d|\  }}n|dv rI|t          d|z            |s fd}d|v r|                    d          |d<    | |f||dd|\  }}n|dv rj|t          d|z            |st          d|z            |st          d|z            d|v r|                    d          |d<    | |f|||d|\  }}nt          d|z            |r j        }||_        |S )aV  
    Find a root of a scalar function.

    Parameters
    ----------
    f : callable
        A function to find a root of.
    args : tuple, optional
        Extra arguments passed to the objective function and its derivative(s).
    method : str, optional
        Type of solver.  Should be one of

            - 'bisect'    :ref:`(see here) <optimize.root_scalar-bisect>`
            - 'brentq'    :ref:`(see here) <optimize.root_scalar-brentq>`
            - 'brenth'    :ref:`(see here) <optimize.root_scalar-brenth>`
            - 'ridder'    :ref:`(see here) <optimize.root_scalar-ridder>`
            - 'toms748'    :ref:`(see here) <optimize.root_scalar-toms748>`
            - 'newton'    :ref:`(see here) <optimize.root_scalar-newton>`
            - 'secant'    :ref:`(see here) <optimize.root_scalar-secant>`
            - 'halley'    :ref:`(see here) <optimize.root_scalar-halley>`

    bracket: A sequence of 2 floats, optional
        An interval bracketing a root.  `f(x, *args)` must have different
        signs at the two endpoints.
    x0 : float, optional
        Initial guess.
    x1 : float, optional
        A second guess.
    fprime : bool or callable, optional
        If `fprime` is a boolean and is True, `f` is assumed to return the
        value of the objective function and of the derivative.
        `fprime` can also be a callable returning the derivative of `f`. In
        this case, it must accept the same arguments as `f`.
    fprime2 : bool or callable, optional
        If `fprime2` is a boolean and is True, `f` is assumed to return the
        value of the objective function and of the
        first and second derivatives.
        `fprime2` can also be a callable returning the second derivative of `f`.
        In this case, it must accept the same arguments as `f`.
    xtol : float, optional
        Tolerance (absolute) for termination.
    rtol : float, optional
        Tolerance (relative) for termination.
    maxiter : int, optional
        Maximum number of iterations.
    options : dict, optional
        A dictionary of solver options. E.g., ``k``, see
        :obj:`show_options()` for details.

    Returns
    -------
    sol : RootResults
        The solution represented as a ``RootResults`` object.
        Important attributes are: ``root`` the solution , ``converged`` a
        boolean flag indicating if the algorithm exited successfully and
        ``flag`` which describes the cause of the termination. See
        `RootResults` for a description of other attributes.

    See also
    --------
    show_options : Additional options accepted by the solvers
    root : Find a root of a vector function.

    Notes
    -----
    This section describes the available solvers that can be selected by the
    'method' parameter.

    The default is to use the best method available for the situation
    presented.
    If a bracket is provided, it may use one of the bracketing methods.
    If a derivative and an initial value are specified, it may
    select one of the derivative-based methods.
    If no method is judged applicable, it will raise an Exception.

    Arguments for each method are as follows (x=required, o=optional).

    +-----------------------------------------------+---+------+---------+----+----+--------+---------+------+------+---------+---------+
    |                    method                     | f | args | bracket | x0 | x1 | fprime | fprime2 | xtol | rtol | maxiter | options |
    +===============================================+===+======+=========+====+====+========+=========+======+======+=========+=========+
    | :ref:`bisect <optimize.root_scalar-bisect>`   | x |  o   |    x    |    |    |        |         |  o   |  o   |    o    |   o     |
    +-----------------------------------------------+---+------+---------+----+----+--------+---------+------+------+---------+---------+
    | :ref:`brentq <optimize.root_scalar-brentq>`   | x |  o   |    x    |    |    |        |         |  o   |  o   |    o    |   o     |
    +-----------------------------------------------+---+------+---------+----+----+--------+---------+------+------+---------+---------+
    | :ref:`brenth <optimize.root_scalar-brenth>`   | x |  o   |    x    |    |    |        |         |  o   |  o   |    o    |   o     |
    +-----------------------------------------------+---+------+---------+----+----+--------+---------+------+------+---------+---------+
    | :ref:`ridder <optimize.root_scalar-ridder>`   | x |  o   |    x    |    |    |        |         |  o   |  o   |    o    |   o     |
    +-----------------------------------------------+---+------+---------+----+----+--------+---------+------+------+---------+---------+
    | :ref:`toms748 <optimize.root_scalar-toms748>` | x |  o   |    x    |    |    |        |         |  o   |  o   |    o    |   o     |
    +-----------------------------------------------+---+------+---------+----+----+--------+---------+------+------+---------+---------+
    | :ref:`secant <optimize.root_scalar-secant>`   | x |  o   |         | x  | o  |        |         |  o   |  o   |    o    |   o     |
    +-----------------------------------------------+---+------+---------+----+----+--------+---------+------+------+---------+---------+
    | :ref:`newton <optimize.root_scalar-newton>`   | x |  o   |         | x  |    |   o    |         |  o   |  o   |    o    |   o     |
    +-----------------------------------------------+---+------+---------+----+----+--------+---------+------+------+---------+---------+
    | :ref:`halley <optimize.root_scalar-halley>`   | x |  o   |         | x  |    |   x    |    x    |  o   |  o   |    o    |   o     |
    +-----------------------------------------------+---+------+---------+----+----+--------+---------+------+------+---------+---------+

    Examples
    --------

    Find the root of a simple cubic

    >>> from scipy import optimize
    >>> def f(x):
    ...     return (x**3 - 1)  # only one real root at x = 1

    >>> def fprime(x):
    ...     return 3*x**2

    The `brentq` method takes as input a bracket

    >>> sol = optimize.root_scalar(f, bracket=[0, 3], method='brentq')
    >>> sol.root, sol.iterations, sol.function_calls
    (1.0, 10, 11)

    The `newton` method takes as input a single point and uses the
    derivative(s).

    >>> sol = optimize.root_scalar(f, x0=0.2, fprime=fprime, method='newton')
    >>> sol.root, sol.iterations, sol.function_calls
    (1.0, 11, 22)

    The function can provide the value and derivative(s) in a single call.

    >>> def f_p_pp(x):
    ...     return (x**3 - 1), 3*x**2, 6*x

    >>> sol = optimize.root_scalar(
    ...     f_p_pp, x0=0.2, fprime=True, method='newton'
    ... )
    >>> sol.root, sol.iterations, sol.function_calls
    (1.0, 11, 11)

    >>> sol = optimize.root_scalar(
    ...     f_p_pp, x0=0.2, fprime=True, fprime2=True, method='halley'
    ... )
    >>> sol.root, sol.iterations, sol.function_calls
    (1.0, 7, 8)


    NFT)xtolrtolmaxiter)full_outputdispr	   r   r   r   zIUnable to select a solver as neither bracket nor starting point provided.)r   r   zUnknown solver %s)r   r   r	   r
   r   zBracket needed for %sr%   r   _x)root
iterationsfunction_callsflagmethod)r   zx0 must not be None for %sr/   tol)r   r"   r&   x1)r   c                 6    t          | d|          d         S )Nz2-point)r9   r   r   r   )r   r   fs     r   r"   zroot_scalar.<locals>.fprime2  s!    
 )AidKKKANNr   )r   r"   r&   )r   zfprime must be specified for %sz fprime2 must be specified for %s)
isinstancetuplecallableboolr   r&   r"   localsgetupdate
ValueErrorlowergetattroptzerosAttributeErrorlistnpndarrayhasattrRootResultsr4   nan_function_callsstrpopr   r7   )r=   r   r9   bracketr"   r&   x0r;   r/   r0   r1   optionsis_memoizedkwargskvmethmap2underlyingmethodceabrsolr   s   `                        r   r   r   >   s   d dE"" w K8G#4#4== 	1AKiGXFFG(6"2"2<< 	1AKXFFF F(  HHLLOO=F1I  g MMdM///  " 	"FF^ " &%FF%FF!! 9 8 9 9 	9 <<>>D (H==N<(N$6$6tT$B$BCC < < <,t344!;< BBB'D%#<== 	?4v=>>>rr{1	WQ1::4:6::FAss 	 	 	
 q$ *68f:;:K03AvG G G
  	 
		:9FBCCCV"JJv..F5MB *T$* *"(* *33			:9FBCCC 	OO O O O O V"JJv..F5MB #T&$ # #!# #33			:9FBCCC 	I>GHHH 	J?&HIIIV"JJv..F5MBTT&'TTVTT33,v5666 % )$Js1   ?)E) )
F3FFG+ +
I5AIIc                      dS )a?  
    Options
    -------
    args : tuple, optional
        Extra arguments passed to the objective function.
    bracket: A sequence of 2 floats, optional
        An interval bracketing a root.  `f(x, *args)` must have different
        signs at the two endpoints.
    xtol : float, optional
        Tolerance (absolute) for termination.
    rtol : float, optional
        Tolerance (relative) for termination.
    maxiter : int, optional
        Maximum number of iterations.
    options: dict, optional
        Specifies any method-specific options not covered above

    Nr-   r-   r   r   _root_scalar_brentq_docrc   S  	    & 	Dr   c                      dS a@  
    Options
    -------
    args : tuple, optional
        Extra arguments passed to the objective function.
    bracket: A sequence of 2 floats, optional
        An interval bracketing a root.  `f(x, *args)` must have different
        signs at the two endpoints.
    xtol : float, optional
        Tolerance (absolute) for termination.
    rtol : float, optional
        Tolerance (relative) for termination.
    maxiter : int, optional
        Maximum number of iterations.
    options: dict, optional
        Specifies any method-specific options not covered above.

    Nr-   r-   r   r   _root_scalar_brenth_docrg   i  rd   r   c                      dS rf   r-   r-   r   r   _root_scalar_toms748_docri   ~  rd   r   c                      dS )a  
    Options
    -------
    args : tuple, optional
        Extra arguments passed to the objective function.
    xtol : float, optional
        Tolerance (absolute) for termination.
    rtol : float, optional
        Tolerance (relative) for termination.
    maxiter : int, optional
        Maximum number of iterations.
    x0 : float, required
        Initial guess.
    x1 : float, required
        A second guess.
    options: dict, optional
        Specifies any method-specific options not covered above.

    Nr-   r-   r   r   _root_scalar_secant_docrk     s	    ( 	Dr   c                      dS )a"  
    Options
    -------
    args : tuple, optional
        Extra arguments passed to the objective function and its derivative.
    xtol : float, optional
        Tolerance (absolute) for termination.
    rtol : float, optional
        Tolerance (relative) for termination.
    maxiter : int, optional
        Maximum number of iterations.
    x0 : float, required
        Initial guess.
    fprime : bool or callable, optional
        If `fprime` is a boolean and is True, `f` is assumed to return the
        value of derivative along with the objective function.
        `fprime` can also be a callable returning the derivative of `f`. In
        this case, it must accept the same arguments as `f`.
    options: dict, optional
        Specifies any method-specific options not covered above.

    Nr-   r-   r   r   _root_scalar_newton_docrm     s	    . 	Dr   c                      dS )ar  
    Options
    -------
    args : tuple, optional
        Extra arguments passed to the objective function and its derivatives.
    xtol : float, optional
        Tolerance (absolute) for termination.
    rtol : float, optional
        Tolerance (relative) for termination.
    maxiter : int, optional
        Maximum number of iterations.
    x0 : float, required
        Initial guess.
    fprime : bool or callable, required
        If `fprime` is a boolean and is True, `f` is assumed to return the
        value of derivative along with the objective function.
        `fprime` can also be a callable returning the derivative of `f`. In
        this case, it must accept the same arguments as `f`.
    fprime2 : bool or callable, required
        If `fprime2` is a boolean and is True, `f` is assumed to return the
        value of 1st and 2nd derivatives along with the objective function.
        `fprime2` can also be a callable returning the 2nd derivative of `f`.
        In this case, it must accept the same arguments as `f`.
    options: dict, optional
        Specifies any method-specific options not covered above.

    Nr-   r-   r   r   _root_scalar_halley_docro     s	    8 	Dr   c                      dS rf   r-   r-   r   r   _root_scalar_ridder_docrq     rd   r   c                      dS rf   r-   r-   r   r   _root_scalar_bisect_docrs     rd   r   )r-   NNNNNNNNNN)r,   numpyrK    r   rH   _numdiffr   __all__ROOT_SCALAR_METHODSr   r   rc   rg   ri   rk   rm   ro   rq   rs   r-   r   r   <module>ry      s/        # # # # # # ' ' ' ' ' '/5 5 5 ' ' ' ' ' ' ' 'T 26%) .2	R R R Rj	 	 	,	 	 	*	 	 	,	 	 	.	 	 	4	 	 	>	 	 	,	 	 	 	 	r   