code: def brentq(
      objective_fn: Callable[[types.RealTensor], types.RealTensor],
      left_bracket: types.RealTensor,
      right_bracket: types.RealTensor,
      value_at_left_bracket: types.RealTensor = None,
      value_at_right_bracket: types.RealTensor = None,
      absolute_root_tolerance: types.RealTensor = 2e-7,
      relative_root_tolerance: types.RealTensor = None,
      function_tolerance: types.RealTensor = 2e-7,
      max_iterations: types.IntTensor = 100,
      stopping_policy_fn: Callable[
          [types.BoolTensor], types.BoolTensor
      ] = None,
      validate_args: bool = False,
      name: str = None,
  ) -> BrentResults:
      r"""Finds root(s) of a function of single variable using Brent's method.
  
    [Brent's method](https://en.wikipedia.org/wiki/Brent%27s_method) is a
    root-finding algorithm combining the bisection method, the secant method and
    extrapolation. Like bisection it is guaranteed to converge towards a root if
    one exists, but that convergence is superlinear and on par with less reliable
    methods.
  
    This implementation is a translation of the algorithm described in the
    [original article](https://academic.oup.com/comjnl/article/14/4/422/325237).
  
    #### Examples
  
    ```python
    import tensorflow as tf
    import tf_quant_finance as tff
  
    # Example 1: Roots of a single function for two pairs of starting points.
  
    f = lambda x: 63 * x**5 - 70 * x**3 + 15 * x + 2
    x1 = tf.constant([-10, 1], dtype=tf.float64)
    x2 = tf.constant([10, -1], dtype=tf.float64)
  
    tf.math.brentq(objective_fn=f, left_bracket=x1, right_bracket=x2)
    # ==> BrentResults(
    #    estimated_root=array([-0.14823253, -0.14823253]),
    #    objective_at_estimated_root=array([3.27515792e-15, 0.]),
    #    num_iterations=array([11, 6]),
    #    converged=array([True, True]))
  
    tff.math.root_search.brentq(objective_fn=f,
                                left_bracket=x1,
                                right_bracket=x2,
                                stopping_policy_fn=tf.reduce_any)
    # ==> BrentResults(
    #    estimated_root=array([-2.60718234, -0.14823253]),
    #    objective_at_estimated_root=array([-6.38579115e+03, 2.39763764e-11]),
    #    num_iterations=array([7, 6]),
    #    converged=array([False, True]))
    ```
  
    # Example 2: Roots of a multiplex function for one pair of starting points.
  
    def f(x):
      return tf.constant([0., 63.], dtype=tf.float64) * x**5 \
          + tf.constant([5., -70.], dtype=tf.float64) * x**3 \
          + tf.constant([-3., 15.], dtype=tf.float64) * x \
          + 2
  
    x1 = tf.constant([-5, -5], dtype=tf.float64)
    x2 = tf.constant([5, 5], dtype=tf.float64)
  
    tff.math.root_search.brentq(objective_fn=f, left_bracket=x1, right_bracket=x2)
    # ==> BrentResults(
    #    estimated_root=array([-1., -0.14823253]),
    #    objective_at_estimated_root=array([0., 2.08721929e-14]),
    #    num_iterations=array([13, 11]),
    #    converged=array([True, True]))
  
    # Example 3: Roots of a multiplex function for two pairs of starting points.
  
    def f(x):
      return tf.constant([0., 63.], dtype=tf.float64) * x**5 \
          + tf.constant([5., -70.], dtype=tf.float64) * x**3 \
          + tf.constant([-3., 15.], dtype=tf.float64) * x \
          + 2
  
    x1 = tf.constant([[-5, -5], [10, 10]], dtype=tf.float64)
    x2 = tf.constant([[5, 5], [-10, -10]], dtype=tf.float64)
  
    tff.math.root_search.brentq(objective_fn=f, left_bracket=x1, right_bracket=x2)
    # ==> BrentResults(
    #    estimated_root=array([
    #        [-1, -0.14823253],
    #        [-1, -0.14823253]]),
    #    objective_at_estimated_root=array([
    #        [0., 2.08721929e-14],
    #        [0., 2.08721929e-14]]),
    #    num_iterations=array([
    #        [13, 11],
    #        [15, 11]]),
    #    converged=array([
    #        [True, True],
    #        [True, True]]))
    ```
  
    Args:
      objective_fn: Python callable for which roots are searched. It must be a
        callable of a single `Tensor` parameter and return a `Tensor` of the same
        shape and dtype as `left_bracket`.
      left_bracket: `Tensor` or Python float representing the first starting
        points. The function will search for roots between each pair of points
        defined by `left_bracket` and `right_bracket`. The shape of `left_bracket`
        should match that of the input to `objective_fn`.
      right_bracket: `Tensor` of the same shape and dtype as `left_bracket` or
        Python float representing the second starting points. The function will
        search for roots between each pair of points defined by `left_bracket` and
        `right_bracket`. This argument must have the same shape as `left_bracket`.
      value_at_left_bracket: Optional `Tensor` or Python float representing the
        value of `objective_fn` at `left_bracket`. If specified, this argument
        must have the same shape as `left_bracket`. If not specified, the value
        will be evaluated during the search.
        Default value: None.
      value_at_right_bracket: Optional `Tensor` or Python float representing the
        value of `objective_fn` at `right_bracket`. If specified, this argument
        must have the same shape as `right_bracket`. If not specified, the value
        will be evaluated during the search.
        Default value: None.
      absolute_root_tolerance: Optional `Tensor` representing the absolute
        tolerance for estimated roots, with the total tolerance being calculated
        as `(absolute_root_tolerance + relative_root_tolerance * |root|) / 2`. If
        specified, this argument must be positive, broadcast with the shape of
        `left_bracket` and have the same dtype.
        Default value: `2e-7`.
      relative_root_tolerance: Optional `Tensor` representing the relative
        tolerance for estimated roots, with the total tolerance being calculated
        as `(absolute_root_tolerance + relative_root_tolerance * |root|) / 2`. If
        specified, this argument must be positive, broadcast with the shape of
        `left_bracket` and have the same dtype.
        Default value: `None` which translates to `4 *
          numpy.finfo(left_bracket.dtype.as_numpy_dtype).eps`.
      function_tolerance: Optional `Tensor` representing the tolerance used to
        check for roots. If the absolute value of `objective_fn` is smaller than
        or equal to `function_tolerance` at a given estimate, then that estimate
        is considered a root for the function. If specified, this argument must
        broadcast with the shape of `left_bracket` and have the same dtype. Set to
        zero to match Brent's original algorithm and to continue the search until
        an exact root is found.
        Default value: `2e-7`.
      max_iterations: Optional `Tensor` of an integral dtype or Python integer
        specifying the maximum number of steps to perform for each initial point.
        Must broadcast with the shape of `left_bracket`. If an element is set to
        zero, the function will not search for any root for the corresponding
        points in `left_bracket` and `right_bracket`. Instead, it will return the
        best estimate from the inputs.
        Default value: `100`.
      stopping_policy_fn: Python `callable` controlling the algorithm termination.
        It must be a callable accepting a `Tensor` of booleans with the shape of
        `left_bracket` (each denoting whether the search is finished for each
        starting point), and returning a scalar boolean `Tensor` (indicating
        whether the overall search should stop). Typical values are
        `tf.reduce_all` (which returns only when the search is finished for all
        pairs of points), and `tf.reduce_any` (which returns as soon as the search
        is finished for any pair of points).
        Default value: `None` which translates to `tf.reduce_all`.
      validate_args: Python `bool` indicating whether to validate arguments such
        as `left_bracket`, `right_bracket`, `absolute_root_tolerance`,
        `relative_root_tolerance`, `function_tolerance`, and `max_iterations`.
        Default value: `False`.
      name: Python `str` name prefixed to ops created by this function.
  
    Returns:
      brent_results: A Python object containing the following attributes:
        estimated_root: `Tensor` containing the best estimate explored. If the
          search was successful within the specified tolerance, this estimate is
          a root of the objective function.
        objective_at_estimated_root: `Tensor` containing the value of the
          objective function at `estimated_root`. If the search was successful
          within the specified tolerance, then this is close to 0. It has the
          same dtype and shape as `estimated_root`.
        num_iterations: `Tensor` containing the number of iterations performed.
          It has the same dtype as `max_iterations` and shape as `estimated_root`.
        converged: Scalar boolean `Tensor` indicating whether `estimated_root` is
          a root within the tolerance specified for the search. It has the same
          shape as `estimated_root`.
  
    Raises:
      ValueError: if the `stopping_policy_fn` is not callable.
    """
  
      return _brent(
          objective_fn,
          left_bracket,
          right_bracket,
          value_at_left_bracket=value_at_left_bracket,
          value_at_right_bracket=value_at_right_bracket,
          absolute_root_tolerance=absolute_root_tolerance,
          relative_root_tolerance=relative_root_tolerance,
          function_tolerance=function_tolerance,
          max_iterations=max_iterations,
          stopping_policy_fn=stopping_policy_fn,
          validate_args=validate_args,
          name=name,
      )
  
file_path: tf-quant-finance/tf_quant_finance/math/root_search/brent.py
imports: from typing import Callable
  import tensorflow.compat.v2
  from tf_quant_finance import types
  from tf_quant_finance import utils
  from tf_quant_finance.math.root_search import utils
label_desc: Use image node_id 8 for calling a global function with example usage: brentq(objective_fn, left_bracket, right_bracket, value_at_left_bracket, value_at_right_bracket, absolute_root_tolerance, relative_root_tolerance, function_tolerance, max_iterations, stopping_policy_fn, validate_args, name) and returns: _brent