o
    Qep                 
   @   s@  d Z ddlmZ ddl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mZ d	dlmZ d	dlmZmZmZ ddlZddlmZ ddlmZmZmZmZmZ ddlmZ ddlmZ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+ d	dl(m,Z, d	dl(m-Z- d	dl(m.Z. d	dl(m/Z/ d	dl(m0Z0 d	dl(m1Z1 d	dl(m2Z2 d	dl(m3Z3 d	d l(m4Z4 d	d!l(m5Z5 d	d"l(m6Z6 d	d#l(m7Z7 d	d$l(m8Z8 d	d%l(m9Z9 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(m?Z? d	d,l(m@Z@ d	d-l(mAZA d	d.l(mBZB d	d/l(mCZC d	d0l(mDZD d	d1l(mEZE dd2l&mFZF dd3lmGZGmHZH g ZIejJjKejJjLejJjMejJjNejJjOgZPejJjQejJjRgZSdd4d5ZTdd9d:ZUdd=d>ZVdd?d@ZWe%ddAdBZXddCdDZYdEdFdGdHdIdJdKdLdMdN	ZZe	O		P	ddQdRZ[dSdT Z\ddUdIZ]e%ddVdWZ^ddXdJZ_e%ddYdZZ`dd[dLZadd\dHZbdd]dMZce%dd^d_ZdecZeecZfdd`dKZgddadEZhddbdFZiddcddZjddedfZkddgdhZlddidjZmddkdlZnddmdnZoe	dhdoddpdqZpddrdsZqddtduZrddvdwZsdxdy Ztddzd{Zudd|d}Zvdd~dZwdddZxdd Zydd Zzdd Z{dddZ|dddZ}dddZ~dddZdddZdddZdddZdddZe%dddZdddZdddZe	ddodddZdddZdddZdddZdddZdddZdddZdddZdddZdddZe%dddZdddZdddZdddZdd ZdddZdddZdddZdddÄZdddńZdddǄZdddɄZe%ddd˄Zddd̈́Ze%dddτZdddфZdddӄZdddՄZdddׄZdddلZdddۄZddd݄Zddd߄ZdddZdddZdS )z
math functions
    )print_functionN)VarDesc)dygraph_only)OpProtoHolder)templatedoc)dygraph_utils   )cast)_complex_to_real_dtype)_generate_doc_string_generate_activation_fngenerate_layer_fn   )Variable)corein_dygraph_mode_non_static_modeLayerHelper_in_legacy_dygraph)r   )_varbase_creatorconvert_np_dtype_to_dtype_)check_variable_and_dtype
check_typecheck_dtypeconvert_dtype)inplace_apis_in_dygraph_only)utils)abs)acos)asin)ceil)ceil_)cos)tan)sinh)cosh)exp)exp_)expm1)floor)floor_)
reciprocal)reciprocal_)round)round_)rsqrt)rsqrt_)square)atan)erf)sqrt)sqrt_)sin)asinh)acosh)atanh)elementwise_sub)_C_ops_legacy_C_opsc                 C   ~   t  rt| S t rt| S t| dddgd d| gi}td
i t }|jdd}|	|}|j
dd| id|id |S )a  
    Calculates the natural log of the given input Tensor, element-wise.

    .. math::

        Out = \ln(x)

    Args:
        x (Tensor): Input Tensor. Must be one of the following types: float32, float64.
        name (str|None): The default value is None. Normally there is no need for user to set this property. For more information, please refer to :ref:`api_guide_Name`


    Returns:
        Tensor: The natural log of the input Tensor computed element-wise.

    Examples:

        .. code-block:: python

            import paddle

            x = [[2,3,4], [7,8,9]]
            x = paddle.to_tensor(x, dtype='float32')
            res = paddle.log(x)
            # [[0.693147, 1.09861, 1.38629], [1.94591, 2.07944, 2.19722]]
    xfloat32float64logXZinput_param_nameOuttypeinputsoutputsN)rA   )r   r;   rA   r   r<   r   r   localsinput_dtype"create_variable_for_type_inference	append_opr>   namerG   helperdtypeout rR   BD:\Projects\ConvertPro\env\Lib\site-packages\paddle/tensor/math.pyrA   j   s   



rA         ?        Tc              	   C   s   t  rt| |t||}t||S t r9t|tr"|	 
dn|}t| dt|dt|d|}t||S t| dg dd d| gi}t||d}	t|trY|g|d	< nt||	d< tdi t }
|
j| jd
}|
jd|d|i|	d |
|S )ag  
    Scale operator.

    Putting scale and bias to the input Tensor as following:

    ``bias_after_scale`` is True:

    .. math::
                            Out=scale*X+bias

    ``bias_after_scale`` is False:

    .. math::
                            Out=scale*(X+bias)

    Args:
        x (Tensor): Input N-D Tensor of scale operator. Data type can be float32, float64, int8, int16, int32, int64, uint8.
        scale (float|Tensor): The scale factor of the input, it should be a float number or a Tensor with shape [1] and data type as float32.
        bias (float): The bias to be put on the input.
        bias_after_scale (bool): Apply bias addition after or before scaling. It is useful for numeric stability in some circumstances.
        act (str, optional): Activation applied to the output such as tanh, softmax, sigmoid, relu.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: Output Tensor of scale operator, with shape and data type same as input.

    Examples:
        .. code-block:: python
            
            # scale as a float32 number
            import paddle

            data = paddle.randn(shape=[2,3], dtype='float32')
            res = paddle.scale(data, scale=2.0, bias=1.0)

        .. code-block:: python

            # scale with parameter scale as a Tensor
            import paddle

            data = paddle.randn(shape=[2, 3], dtype='float32')
            factor = paddle.to_tensor([2], dtype='float32')
            res = paddle.scale(data, scale=factor, bias=1.0)

    r   scalebiasbias_after_scaler>   )	float16uint16r?   r@   Zint8int16int32int64Zuint8rB   )rW   rX   ZScaleTensorrP   rD   rF   rG   rH   attrsNrV   )r   r;   rV   floatr   _append_activation_in_dygraphr   
isinstancer   numpyitemr<   r   r   rI   rK   rP   rL   append_activation)r>   rV   rW   rX   actrN   rQ   _scalerG   r`   rO   rR   rR   rS   rV      s4   /



rV   q=
ףp?jMSt?c                 C   sl   t  rt| d|d|S t| dg dd tdi t }|j| jd}|jdd| id|i||d	d
 |S )aP  
    stanh activation.

    .. math::

        out = b * rac{e^{a * x} - e^{-a * x}}{e^{a * x} + e^{-a * x}}

    Parameters:
        x (Tensor): The input Tensor with data type float32, float64.
        scale_a (float, optional): The scale factor a of the input. Default is 0.67.
        scale_b (float, optional): The scale factor b of the output. Default is 1.7159.
        name (str, optional): Name for the operation (optional, default is None).
            For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        A Tensor with the same data type and shape as ``x`` .

    Examples:
        .. code-block:: python

            import paddle

            x = paddle.to_tensor([1.0, 2.0, 3.0, 4.0])
            out = paddle.stanh(x, scale_a=0.67, scale_b=1.72) # [1.00616539, 1.49927628, 1.65933108, 1.70390463]

    scale_ascale_br>   rY   r?   r@   stanhr^   rB   rD   )rl   rm   r_   N)ro   )	r   r<   ro   r   r   rI   rK   rP   rL   )r>   rl   rm   rN   rO   rQ   rR   rR   rS   ro      s   ro   c                 C   s   t  r	t| |S t rt|| S tdi t }t| dtd t	| dk r+t
dt| D ]\}}t|dt| d g dd q/t|dd	d
gd || d j}|jd| |dd|gid |S )a4	  

    Based on the given index parameter, the OP selects a specific row from each input Tensor to construct the output Tensor.

    If the input of this OP contains :math:`m` Tensors, where :math:`I_{i}` means the i-th input Tensor, :math:`i` between :math:`[0,m)` .

    And :math:`O` means the output, where :math:`O[i]` means the i-th row of the output, then the output satisfies that :math:`O[i] = I_{index[i]}[i]` .

    For Example:

            .. code-block:: text

                Given:

                inputs = [[[0,0,3,4], [0,1,3,4], [0,2,4,4], [0,3,3,4]],
                          [[1,0,3,4], [1,1,7,8], [1,2,4,2], [1,3,3,4]],
                          [[2,0,3,4], [2,1,7,8], [2,2,4,2], [2,3,3,4]],
                          [[3,0,3,4], [3,1,7,8], [3,2,4,2], [3,3,3,4]]]

                index = [[3],[0],[1],[2]]

                out = [[3,0,3,4],    # out[0] = inputs[index[0]][0] = inputs[3][0] = [3,0,3,4]
                       [0,1,3,4],    # out[1] = inputs[index[1]][1] = inputs[0][1] = [0,1,3,4]
                       [1,2,4,2],    # out[2] = inputs[index[2]][2] = inputs[1][2] = [1,2,4,2]
                       [2,3,3,4]]    # out[3] = inputs[index[3]][3] = inputs[2][3] = [2,3,3,4]


    Args:
        inputs (list): The input Tensor list. The list elements are N-D Tensors of data types float32, float64, int32, int64. All input Tensor shapes should be the same and rank must be at least 2.
        index (Tensor): Used to select some rows in the input Tensor to construct an index of the output Tensor. It is a 2-D Tensor with data type int32 or int64 and shape [M, 1], where M is the number of input Tensors.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: Output of multiplex OP, with data type being float32, float64, int32, int64.

    Examples:

        .. code-block:: python

            import paddle
            
            img1 = paddle.to_tensor([[1, 2], [3, 4]], dtype=paddle.float32)
            img2 = paddle.to_tensor([[5, 6], [7, 8]], dtype=paddle.float32)
            inputs = [img1, img2]
            index = paddle.to_tensor([[1], [0]], dtype=paddle.int32)
            res = paddle.multiplex(inputs, index)
            print(res) # Tensor([[5., 6.], [3., 4.]], dtype=float32)

    	multiplexrG   r   z8inputs should be a list object with at least 2 elements.zinput[]r?   r@   r\   r]   indexr\   r]   r   )rB   ZIdsrD   rE   N)rp   )r   r;   rp   r   r<   r   rI   r   listlen
ValueError	enumerater   strrK   rP   rL   )rG   rs   rN   rO   idr>   rQ   rR   rR   rS   rp     s2   2rp   c              	   C   s^   t  rt| |t||S t r-t|tr| dn|}t	| dt|dt|d|S dS )z
    Inplace version of ``scale`` API, the output Tensor will be inplaced with input ``x``.
    Please refer to :ref:`api_tensor_scale`.
    r   rV   rW   rX   N)
r   r;   scale_rb   r   rd   r   re   rf   r<   )r>   rV   rW   rX   rh   rN   ri   rR   rR   rS   rz   W  s   
rz   c                 C   sD  t  r%t|ttfrt| |S t|tjtfrt	| |S t
d|j t rNt|ttfr6t| d|S t|tjtfrGt| |ddddS t
d|j t|ttfrytdi t }d| i}d|i}|j| jd	}|jd|d
|i|d |S t|tjtfrtdi t }|j| jd	}ttdi t S t
dt| )a$  
    Compute the power of Tensor elements. The equation is:

    .. math::
        out = x^{y} 

    Note:
        ``paddle.pow`` supports broadcasting. If you want know more about broadcasting, please refer to :ref:`user_guide_broadcasting` .


    Args:
        x (Tensor): An N-D Tensor, the data type is float16, float32, float64, int32 or int64.
        y (float|int|Tensor): If it is an N-D Tensor, its data type should be the same as `x`.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.
    
    Returns:
        N-D Tensor. A location into which the result is stored. Its dimension and data type are the same as `x`.

    Examples:

        ..  code-block:: python

            import paddle

            x = paddle.to_tensor([1, 2, 3], dtype='float32')

            # example 1: y is a float or int
            res = paddle.pow(x, 2)
            print(res)
            # Tensor(shape=[3], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #        [1., 4., 9.])
            res = paddle.pow(x, 2.5)
            print(res)
            # Tensor(shape=[3], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #        [1.         , 5.65685415 , 15.58845711])

            # example 2: y is a Tensor
            y = paddle.to_tensor([2], dtype='float32')
            res = paddle.pow(x, y)
            print(res)
            # Tensor(shape=[3], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #        [1., 4., 9.])

    z2y must be scalar or tensor type, but received: %s factorNelementwise_powaxisrh   op_namepowrB   r^   rD   r_   )r   )r}   )r   rd   intrb   r;   r   paddleTensorr   r}   	TypeErrorrP   r   r<   _elementwise_op_in_dygraphr   rI   rK   rL   _elementwise_oprF   )r>   yrN   rO   rG   r`   rQ   rR   rR   rS   r   f  s8   .
r   maximumminimumr}   floor_divideaddsubtractmultiplydivide	remainder)	elementwise_maxelementwise_minr}   elementwise_floordivelementwise_addr:   elementwise_mulelementwise_divelementwise_modr|   Fc           	      C   s   dd }|t  vs|dkrtt|}|| |d|d|}n&t r2tt||s*t | n|}|| |}t rCtt|}|| |d|d|}tj|||dS )Nc                 S   s   | d dkS )Nr|   _rR   )r   rR   rR   rS   
is_inplace  s   z._elementwise_op_in_dygraph.<locals>.is_inplacer|   r   
use_mkldnn)r   )	OP_NAMEMAPPINGkeysgetattrr<   r   r;   r   r   rc   )	r>   r   r   rh   r   r   r   oprQ   rR   rR   rS   r     s   


r   c           	      C   s  | j }| jd|}| jdd }| jdd }| jdd }|d us*J d||d us5J d|t|dg d| t|dg d| | jdd	}| jd
d}| jdd }|d u ru|d u rl| j|jd}n	| j||jdd}| j|||dd|i||dd | 	|S )Noriginal_op_typer>   r   rQ   zx cannot be None in {}zy cannot be None in {})rY   r?   r@   r\   r]   boolr   r|   r   FrN   r^   )rN   rP   ZpersistablerB   YrD   )r   r   r_   )
Z
layer_typekwargsgetformatr   rK   rP   Zcreate_variablerL   rg   )	rO   op_typer   r>   r   rQ   r   r   rN   rR   rR   rS   r     sB   


r   c                 C   s8   t  r	t| |S t rt| |S ttdi t S )u  
    Elementwise Add Operator.
    Add two tensors element-wise
    The equation is:

    ..  math::

        Out=X+Y

    $X$ the tensor of any dimension.
    $Y$ the tensor whose dimensions must be less than or equal to the dimensions of $X$.

    There are two cases for this operator:

    1. The shape of $Y$ is the same with $X$.
    2. The shape of $Y$ is a continuous subsequence of $X$.

    For case 2:

    1. Broadcast $Y$ to match the shape of $X$, where axis is the start dimension index for broadcasting $Y$ onto $X$.
    2. If $axis$ is -1 (default), $axis$=rank($X$)−rank($Y$).
    3. The trailing dimensions of size 1 for $Y$ will be ignored for the consideration of subsequence, such as shape($Y$) = (2, 1) => (2).

        For example:

        ..  code-block:: python

            shape(X) = (2, 3, 4, 5), shape(Y) = (,)
            shape(X) = (2, 3, 4, 5), shape(Y) = (5,)
            shape(X) = (2, 3, 4, 5), shape(Y) = (4, 5), with axis=-1(default) or axis=2
            shape(X) = (2, 3, 4, 5), shape(Y) = (3, 4), with axis=1
            shape(X) = (2, 3, 4, 5), shape(Y) = (2), with axis=0
            shape(X) = (2, 3, 4, 5), shape(Y) = (2, 1), with axis=0

    Args:
        x (Tensor): Tensor or LoDTensor of any dimensions. Its dtype should be int32, int64, float32, float64.
        y (Tensor): Tensor or LoDTensor of any dimensions. Its dtype should be int32, int64, float32, float64.
        name (string, optional): For details, please refer to :ref:`api_guide_Name`. Generally, no setting is required. Default: None.

    Returns:
        N-D Tensor. A location into which the result is stored. It’s dimension equals with x.

    Examples:

        ..  code-block:: python

            import paddle

            x = paddle.to_tensor([2, 3, 4], 'float64')
            y = paddle.to_tensor([1, 5, 2], 'float64')
            z = paddle.add(x, y)
            print(z)  # [3., 8., 6. ]
    r   N)r   )	r   r;   r   r   r<   r   r   r   rI   )r>   r   rN   rR   rR   rS   r     s
   7c                 C   sX   d}d}t | j|j}|| jkrtd|| jt r"t| |S t| |||d}|S )z
    Inplace version of ``add`` API, the output Tensor will be inplaced with input ``x``.
    Please refer to :ref:`api_tensor_add`.
    Zelementwise_add_r|   fThe shape of broadcast output {} is different from that of inplace tensor {} in the Inplace operation.r   r   )broadcast_shapeshaperv   r   r   r;   add_r   )r>   r   rN   r   r   	out_shaperQ   rR   rR   rS   r   ?  s   
r   c                 C   L   d}d}d}t  rt| |S t rt| ||||dS tt|fi t S )a  
    Substract two tensors element-wise. The equation is:

    .. math::
        out = x - y

    Note:
        ``paddle.subtract`` supports broadcasting. If you want know more about broadcasting, please refer to :ref:`user_guide_broadcasting` .

    Args:
        x (Tensor): the input tensor, it's data type should be float32, float64, int32, int64.
        y (Tensor): the input tensor, it's data type should be float32, float64, int32, int64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        N-D Tensor. A location into which the result is stored. If x, y have different shapes and are "broadcastable", the resulting tensor shape is the shape of x and y after broadcasting. If x, y have the same shape,  its shape is the same as x and y.

    Examples:

        .. code-block:: python

            import paddle

            x = paddle.to_tensor([[1, 2], [7, 8]])
            y = paddle.to_tensor([[5, 6], [3, 4]])
            res = paddle.subtract(x, y)
            print(res)
            # Tensor(shape=[2, 2], dtype=int64, place=Place(cpu), stop_gradient=True,
            #        [[-4, -4],
            #         [ 4,  4]])

            x = paddle.to_tensor([[[1, 2, 3], [1, 2, 3]]])
            y = paddle.to_tensor([1, 0, 4])
            res = paddle.subtract(x, y)
            print(res)
            # Tensor(shape=[1, 2, 3], dtype=int64, place=Place(cpu), stop_gradient=True,
            #        [[[ 0,  2, -1],
            #          [ 0,  2, -1]]])

            x = paddle.to_tensor([2, float('nan'), 5], dtype='float32')
            y = paddle.to_tensor([1, 4, float('nan')], dtype='float32')
            res = paddle.subtract(x, y)
            print(res)
            # Tensor(shape=[3], dtype=float32, place=Place(cpu), stop_gradient=True,
            #        [1. , nan, nan])

            x = paddle.to_tensor([5, float('inf'), -float('inf')], dtype='float64')
            y = paddle.to_tensor([1, 4, 5], dtype='float64')
            res = paddle.subtract(x, y)
            print(res)
            # Tensor(shape=[3], dtype=float64, place=Place(cpu), stop_gradient=True,
            #        [ 4.  ,  inf., -inf.])
    r:   r|   Nr~   )r   r;   r   r   r   r   r   rI   r>   r   rN   r   r   rh   rR   rR   rS   r   T  s   6
c                 C   sZ   d}d}t | j|j}|| jkrtd|| jt r"t| |S t| |||dd}|S )z
    Inplace version of ``subtract`` API, the output Tensor will be inplaced with input ``x``.
    Please refer to :ref:`api_tensor_subtract`.
    r|   Nr   Zelementwise_sub_r~   )r   r   rv   r   r   r;   	subtract_r   )r>   r   rN   r   rh   r   rQ   rR   rR   rS   r     s   

r   c                 C   r   )aj  
    Divide two tensors element-wise. The equation is:

    .. math::
        out = x / y

    Note:
        ``paddle.divide`` supports broadcasting. If you want know more about broadcasting, please refer to :ref:`user_guide_broadcasting` .

    Args:
        x (Tensor): the input tensor, it's data type should be float32, float64, int32, int64.
        y (Tensor): the input tensor, it's data type should be float32, float64, int32, int64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        N-D Tensor. A location into which the result is stored. If x, y have different shapes and are "broadcastable", the resulting tensor shape is the shape of x and y after broadcasting. If x, y have the same shape,  its shape is the same as x and y.

    Examples:

        ..  code-block:: python

            import paddle

            x = paddle.to_tensor([2, 3, 4], dtype='float64')
            y = paddle.to_tensor([1, 5, 2], dtype='float64')
            z = paddle.divide(x, y)
            print(z)  # [2., 0.6, 2.]

    r   r|   Nr~   )r   r;   r   r   r   r   r   rI   r   rR   rR   rS   r     s   
c                 C   F   d}d}t  rt| |S t rt| |||dS tt|fi t S )a  
    Floor divide two tensors element-wise. The equation is:

    .. math::
        out = x // y

    Note:
        ``paddle.floor_divide`` supports broadcasting. If you want know more about broadcasting, please refer to :ref:`user_guide_broadcasting` .

    Args:
        x (Tensor): the input tensor, it's data type should be int32, int64.
        y (Tensor): the input tensor, it's data type should be int32, int64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        N-D Tensor. A location into which the result is stored. It's dimension equals with $x$.

    Examples:

        ..  code-block:: python

            import paddle

            x = paddle.to_tensor([2, 3, 8, 7])
            y = paddle.to_tensor([1, 5, 3, 3])
            z = paddle.floor_divide(x, y)
            print(z)  # [2, 0, 2, 2]

    r   r|   r   )r   r;   r   r   r   r   r   rI   r>   r   rN   r   r   rR   rR   rS   r     s   c                 C   r   )ad  
    Mod two tensors element-wise. The equation is:

    .. math::

        out = x \% y

    Note:
        ``paddle.remainder`` supports broadcasting. If you want know more about broadcasting, please refer to :ref:`user_guide_broadcasting` .

    Args:
        x (Tensor): the input tensor, it's data type should be float16, float32, float64, int32, int64.
        y (Tensor): the input tensor, it's data type should be float16, float32, float64, int32, int64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        N-D Tensor. A location into which the result is stored. If x, y have different shapes and are "broadcastable", the resulting tensor shape is the shape of x and y after broadcasting. If x, y have the same shape,  its shape is the same as x and y.

    Examples:

        ..  code-block:: python

            import paddle

            x = paddle.to_tensor([2, 3, 8, 7])
            y = paddle.to_tensor([1, 5, 3, 3])
            z = paddle.remainder(x, y)
            print(z)  # [0, 3, 2, 1]

    r   r|   r   )r   r;   r   r   r   r   r   rI   r   rR   rR   rS   r      s   c                 C   sB   d}d}t | j|j}|| jkrtd|| jt| |||dS )z
    Inplace version of ``remainder`` API, the output Tensor will be inplaced with input ``x``.
    Please refer to :ref:`api_tensor_remainder`.
    Zelementwise_mod_r|   r   r   )r   r   rv   r   r   )r>   r   rN   r   r   r   rR   rR   rS   
remainder_+  s   
r   c                 C   sl   d}d}d}t  rt| |S t rt| ||||dS | j|jkr+td| j|jf tt|fi t	 S )aA  
    multiply two tensors element-wise. The equation is:

    .. math::
        out = x * y

    Note:
        ``paddle.multiply`` supports broadcasting. If you would like to know more about broadcasting, please refer to :ref:`user_guide_broadcasting`.

    Args:
        x (Tensor): the input tensor, its data type should be one of float32, float64, int32, int64, bool.
        y (Tensor): the input tensor, its data type should be one of float32, float64, int32, int64, bool.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        N-D Tensor. A location into which the result is stored. If x, y have different shapes and are "broadcastable", the resulting tensor shape is the shape of x and y after broadcasting. If x, y have the same shape,  its shape is the same as x and y.

    Examples:

        ..  code-block:: python

            import paddle

            x = paddle.to_tensor([[1, 2], [3, 4]])
            y = paddle.to_tensor([[5, 6], [7, 8]])
            res = paddle.multiply(x, y)
            print(res) # [[5, 12], [21, 32]]

            x = paddle.to_tensor([[[1, 2, 3], [1, 2, 3]]])
            y = paddle.to_tensor([2])
            res = paddle.multiply(x, y)
            print(res) # [[[2, 4, 6], [2, 4, 6]]]

    r   Nr|   r~   zKInput tensors must be same type, but received type of x: %s, type of y: %s )
r   r;   r   r   r   rP   r   r   r   rI   )r>   r   rN   r   rh   r   rR   rR   rS   r   A  s    #

c                 C   r   )a  
    Compare two tensors and returns a new tensor containing the element-wise maxima. The equation is:

    .. math::
        out = max(x, y)

    Note:
        ``paddle.maximum`` supports broadcasting. If you want know more about broadcasting, please refer to :ref:`user_guide_broadcasting` .

    Args:
        x (Tensor): the input tensor, it's data type should be float32, float64, int32, int64.
        y (Tensor): the input tensor, it's data type should be float32, float64, int32, int64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        N-D Tensor. A location into which the result is stored. If x, y have different shapes and are "broadcastable", the resulting tensor shape is the shape of x and y after broadcasting. If x, y have the same shape,  its shape is the same as x and y.

    Examples:

        .. code-block:: python

            import paddle

            x = paddle.to_tensor([[1, 2], [7, 8]])
            y = paddle.to_tensor([[3, 4], [5, 6]])
            res = paddle.maximum(x, y)
            print(res)
            # Tensor(shape=[2, 2], dtype=int64, place=Place(cpu), stop_gradient=True,
            #        [[3, 4],
            #         [7, 8]])

            x = paddle.to_tensor([[1, 2, 3], [1, 2, 3]])
            y = paddle.to_tensor([3, 0, 4])
            res = paddle.maximum(x, y)
            print(res)
            # Tensor(shape=[2, 3], dtype=int64, place=Place(cpu), stop_gradient=True,
            #        [[3, 2, 4],
            #         [3, 2, 4]])

            x = paddle.to_tensor([2, 3, 5], dtype='float32')
            y = paddle.to_tensor([1, float("nan"), float("nan")], dtype='float32')
            res = paddle.maximum(x, y)
            print(res)
            # Tensor(shape=[3], dtype=float32, place=Place(cpu), stop_gradient=True,
            #        [2. , nan, nan])

            x = paddle.to_tensor([5, 3, float("inf")], dtype='float32')
            y = paddle.to_tensor([1, -float("inf"), 5], dtype='float32')
            res = paddle.maximum(x, y)
            print(res)
            # Tensor(shape=[3], dtype=float32, place=Place(cpu), stop_gradient=True,
            #        [5.  , 3.  , inf.])
    r   r|   Nr~   )r   r;   r   r   r   r   r   rI   r   rR   rR   rS   r   v     6
c                 C   r   )a  
    Compare two tensors and return a new tensor containing the element-wise minima. The equation is:

    .. math::
        out = min(x, y)

    Note:
        ``paddle.minimum`` supports broadcasting. If you want know more about broadcasting, please refer to :ref:`user_guide_broadcasting` .

    Args:
        x (Tensor): the input tensor, it's data type should be float32, float64, int32, int64.
        y (Tensor): the input tensor, it's data type should be float32, float64, int32, int64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor. If x, y have different shapes and are "broadcastable", the resulting tensor shape is the shape of x and y after broadcasting. If x, y have the same shape,  its shape is the same as x and y.

    Examples:

        .. code-block:: python

            import paddle

            x = paddle.to_tensor([[1, 2], [7, 8]])
            y = paddle.to_tensor([[3, 4], [5, 6]])
            res = paddle.minimum(x, y)
            print(res)
            # Tensor(shape=[2, 2], dtype=int64, place=Place(cpu), stop_gradient=True,
            #        [[1, 2],
            #         [5, 6]])

            x = paddle.to_tensor([[[1, 2, 3], [1, 2, 3]]])
            y = paddle.to_tensor([3, 0, 4])
            res = paddle.minimum(x, y)
            print(res)
            # Tensor(shape=[1, 2, 3], dtype=int64, place=Place(cpu), stop_gradient=True,
            #        [[[1, 0, 3],
            #          [1, 0, 3]]])

            x = paddle.to_tensor([2, 3, 5], dtype='float32')
            y = paddle.to_tensor([1, float("nan"), float("nan")], dtype='float32')
            res = paddle.minimum(x, y)
            print(res)
            # Tensor(shape=[3], dtype=float32, place=Place(cpu), stop_gradient=True,
            #        [1. , nan, nan])

            x = paddle.to_tensor([5, 3, float("inf")], dtype='float64')
            y = paddle.to_tensor([1, -float("inf"), 5], dtype='float64')
            res = paddle.minimum(x, y)
            print(res)
            # Tensor(shape=[3], dtype=float64, place=Place(cpu), stop_gradient=True,
            #        [ 1.  , -inf.,  5.  ])
    r   r|   Nr~   )r   r;   r   r   r   r   r   rI   r   rR   rR   rS   r     r   c                 C   N   d}d}d}t  rt| ||S t rt| ||||dS tt|fi t S )a	  
    Compares the elements at the corresponding positions of the two tensors and returns a new tensor containing the maximum value of the element.
    If one of them is a nan value, the other value is directly returned, if both are nan values, then the first nan value is returned.
    The equation is:

    .. math::
        out = fmax(x, y)

    Note:
        ``paddle.fmax`` supports broadcasting. If you want know more about broadcasting, please refer to :ref:`user_guide_broadcasting` .

    Args:
        x (Tensor): the input tensor, it's data type should be float16, float32, float64, int32, int64.
        y (Tensor): the input tensor, it's data type should be float16, float32, float64, int32, int64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        N-D Tensor. A location into which the result is stored. If x, y have different shapes and are "broadcastable", the resulting tensor shape is the shape of x and y after broadcasting. If x, y have the same shape,  its shape is the same as x and y.

    Examples:

        .. code-block:: python

            import paddle

            x = paddle.to_tensor([[1, 2], [7, 8]])
            y = paddle.to_tensor([[3, 4], [5, 6]])
            res = paddle.fmax(x, y)
            print(res)
            # Tensor(shape=[2, 2], dtype=int64, place=Place(cpu), stop_gradient=True,
            #        [[3, 4],
            #         [7, 8]])

            x = paddle.to_tensor([[1, 2, 3], [1, 2, 3]])
            y = paddle.to_tensor([3, 0, 4])
            res = paddle.fmax(x, y)
            print(res)
            # Tensor(shape=[2, 3], dtype=int64, place=Place(cpu), stop_gradient=True,
            #        [[3, 2, 4],
            #         [3, 2, 4]])

            x = paddle.to_tensor([2, 3, 5], dtype='float32')
            y = paddle.to_tensor([1, float("nan"), float("nan")], dtype='float32')
            res = paddle.fmax(x, y)
            print(res)
            # Tensor(shape=[3], dtype=float32, place=Place(cpu), stop_gradient=True,
            #        [2., 3., 5.])

            x = paddle.to_tensor([5, 3, float("inf")], dtype='float32')
            y = paddle.to_tensor([1, -float("inf"), 5], dtype='float32')
            res = paddle.fmax(x, y)
            print(res)
            # Tensor(shape=[3], dtype=float32, place=Place(cpu), stop_gradient=True,
            #        [5.  , 3.  , inf.])
    Zelementwise_fmaxr|   Nr~   )r   r;   fmaxr   r   r   r   rI   r   rR   rR   rS   r        8
r   c                 C   r   )a	  
    Compares the elements at the corresponding positions of the two tensors and returns a new tensor containing the minimum value of the element.
    If one of them is a nan value, the other value is directly returned, if both are nan values, then the first nan value is returned.
    The equation is:

    .. math::
        out = fmin(x, y)

    Note:
        ``paddle.fmin`` supports broadcasting. If you want know more about broadcasting, please refer to :ref:`user_guide_broadcasting` .

    Args:
        x (Tensor): the input tensor, it's data type should be float16, float32, float64, int32, int64.
        y (Tensor): the input tensor, it's data type should be float16, float32, float64, int32, int64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        N-D Tensor. A location into which the result is stored. If x, y have different shapes and are "broadcastable", the resulting tensor shape is the shape of x and y after broadcasting. If x, y have the same shape,  its shape is the same as x and y.

    Examples:

        .. code-block:: python

            import paddle

            x = paddle.to_tensor([[1, 2], [7, 8]])
            y = paddle.to_tensor([[3, 4], [5, 6]])
            res = paddle.fmin(x, y)
            print(res)
            # Tensor(shape=[2, 2], dtype=int64, place=Place(cpu), stop_gradient=True,
            #        [[1, 2],
            #         [5, 6]])

            x = paddle.to_tensor([[[1, 2, 3], [1, 2, 3]]])
            y = paddle.to_tensor([3, 0, 4])
            res = paddle.fmin(x, y)
            print(res)
            # Tensor(shape=[1, 2, 3], dtype=int64, place=Place(cpu), stop_gradient=True,
            #        [[[1, 0, 3],
            #          [1, 0, 3]]])

            x = paddle.to_tensor([2, 3, 5], dtype='float32')
            y = paddle.to_tensor([1, float("nan"), float("nan")], dtype='float32')
            res = paddle.fmin(x, y)
            print(res)
            # Tensor(shape=[3], dtype=float32, place=Place(cpu), stop_gradient=True,
            #        [1., 3., 5.])

            x = paddle.to_tensor([5, 3, float("inf")], dtype='float64')
            y = paddle.to_tensor([1, -float("inf"), 5], dtype='float64')
            res = paddle.fmin(x, y)
            print(res)
            # Tensor(shape=[3], dtype=float64, place=Place(cpu), stop_gradient=True,
            #        [ 1.  , -inf.,  5.  ])
    Zelementwise_fminr|   Nr~   )r   r;   fminr   r   r   r   rI   r   rR   rR   rS   r   8  r   r   c           
      C   s  t |tr|jd t| jkrdnd}n)|dur"t |ttfs"|g}|s&g }t|dkr/d}nt|t| jkr;d}nd}d}|durId}t|}t rTt	| |||S t |tst|dkrg|g krg|dkrg|ndg}t
|rtt
|}t r|rt| d|d|d|d	| jd
|S t| d|d|d|S |||d}|r|| j|d t| dg dd t|dttttdtfd tdi t }|r|j|d}	n|j| jd}	|jdd| id|	i|d |	S )a]  
    Computes the sum of tensor elements over the given dimension.

    Args:
        x (Tensor): An N-D Tensor, the data type is bool, float16, float32, float64, int32 or int64.
        axis (int|list|tuple, optional): The dimensions along which the sum is performed. If
            :attr:`None`, sum all elements of :attr:`x` and return a
            Tensor with a single element, otherwise must be in the
            range :math:`[-rank(x), rank(x))`. If :math:`axis[i] < 0`,
            the dimension to reduce is :math:`rank + axis[i]`.
        dtype (str, optional): The dtype of output Tensor. The default value is None, the dtype
            of output is the same as input Tensor `x`.
        keepdim (bool, optional): Whether to reserve the reduced dimension in the
            output Tensor. The result Tensor will have one fewer dimension
            than the :attr:`x` unless :attr:`keepdim` is true, default
            value is False.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: Results of summation operation on the specified axis of input Tensor `x`,
        if `x.dtype='bool'`, `x.dtype='int32'`, it's data type is `'int64'`, 
        otherwise it's data type is the same as `x`.

    Examples:
        .. code-block:: python

            import paddle

            # x is a Tensor with following elements:
            #    [[0.2, 0.3, 0.5, 0.9]
            #     [0.1, 0.2, 0.6, 0.7]]
            # Each example is followed by the corresponding output tensor.
            x = paddle.to_tensor([[0.2, 0.3, 0.5, 0.9],
                                  [0.1, 0.2, 0.6, 0.7]])
            out1 = paddle.sum(x)  # [3.5]
            out2 = paddle.sum(x, axis=0)  # [0.3, 0.5, 1.1, 1.6]
            out3 = paddle.sum(x, axis=-1)  # [1.9, 1.6]
            out4 = paddle.sum(x, axis=1, keepdim=True)  # [[1.9], [1.6]]

            # y is a Tensor with shape [2, 2, 2] and elements as below:
            #      [[[1, 2], [3, 4]],
            #      [[5, 6], [7, 8]]]
            # Each example is followed by the corresponding output tensor.
            y = paddle.to_tensor([[[1, 2], [3, 4]], 
                                  [[5, 6], [7, 8]]])
            out5 = paddle.sum(y, axis=[1, 2]) # [10, 26]
            out6 = paddle.sum(y, axis=[0, 1]) # [16, 20]
            
            # x is a Tensor with following elements:
            #    [[True, True, True, True]
            #     [False, False, False, False]]
            # Each example is followed by the corresponding output tensor.
            x = paddle.to_tensor([[True, True, True, True],
                                  [False, False, False, False]])
            out7 = paddle.sum(x)  # [4]
            out8 = paddle.sum(x, axis=0)  # [1, 1, 1, 1]
            out9 = paddle.sum(x, axis=1)  # [4, 0]
    r   TFNrR   dimkeep_dim
reduce_allin_dtype	out_dtyper   r   r   r   r   r>   )r   rY   r?   r@   r[   r\   r]   	complex64
complex128r   rY   r?   r@   r\   r]   r   r   sumr   r^   
reduce_sumrB   rD   r_   )r   )rd   r   r   ru   rt   tupler   r   r;   r   r   _contain_var_convert_to_tensor_listr   r<   r   rP   updater   r   r   rF   r   rI   rK   rL   )
r>   r   rP   keepdimrN   reduce_all_flagZ
dtype_flagr`   rO   rQ   rR   rR   rS   r   {  sr   
;
"


r   c                 C   sX   t | dg dd t|dttttdfd t| }tt	| || }t
|||||S )a=	  
    Computes the sum of tensor elements over the given axis, treating Not a Numbers (NaNs) as zero.

    Args:
        x (Tensor): An N-D Tensor, the data type is float32, float64, int32 or int64.
        axis (int|list|tuple, optional): The dimensions along which the nansum is performed. If
            :attr:`None`, nansum all elements of :attr:`x` and return a
            Tensor with a single element, otherwise must be in the
            range :math:`[-rank(x), rank(x))`. If :math:`axis[i] < 0`,
            the dimension to reduce is :math:`rank + axis[i]`.
        dtype (str, optional): The dtype of output Tensor. The default value is None, the dtype
            of output is the same as input Tensor `x`.
        keepdim (bool, optional): Whether to reserve the reduced dimension in the
            output Tensor. The result Tensor will have one fewer dimension
            than the :attr:`x` unless :attr:`keepdim` is true, default
            value is False.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: Results of summation operation on the specified axis of input Tensor `x`,

    Examples:
        .. code-block:: python

            import paddle

            # x is a Tensor with following elements:
            #    [[nan, 0.3, 0.5, 0.9]
            #     [0.1, 0.2, -nan, 0.7]]
            # Each example is followed by the corresponding output tensor.
            x = paddle.to_tensor([[float('nan'), 0.3, 0.5, 0.9],
                            [0.1, 0.2, float('-nan'), 0.7]],dtype="float32")
            out1 = paddle.nansum(x)  # [2.7]
            out2 = paddle.nansum(x, axis=0)  # [0.1, 0.5, 0.5, 1.6]
            out3 = paddle.nansum(x, axis=-1)  # [1.7, 1.0]
            out4 = paddle.nansum(x, axis=1, keepdim=True)  # [[1.7], [1.0]]

            # y is a Tensor with shape [2, 2, 2] and elements as below:
            #      [[[1, nan], [3, 4]],
            #      [[5, 6], [-nan, 8]]]
            # Each example is followed by the corresponding output tensor.
            y = paddle.to_tensor([[[1, float('nan')], [3, 4]],
                            [[5, 6], [float('-nan'), 8]]])
            out5 = paddle.nansum(y, axis=[1, 2]) # [8, 19]
            out6 = paddle.nansum(y, axis=[0, 1]) # [9, 18]
    r>   rr   nansumr   N)r   r   r   rt   r   rF   r   
zeros_likewhereisnanr   )r>   r   rP   r   rN   Zzero_tensorZ
tmp_tensorrR   rR   rS   r     s   /
r   c                 C   sx   t |tr|g}t| dg dd |durt|dtttfd tjt|  ||d}t	tj
| |||d|| jS )a	  
    Compute the arithmetic mean along the specified axis, ignoring NaNs.

    Args:
        x (Tensor): The input Tensor with data type uint16, float16, float32, float64.
        axis (int|list|tuple, optional):The axis along which to perform nanmean
            calculations. ``axis`` should be int, list(int) or tuple(int). If
            ``axis`` is a list/tuple of dimension(s), nanmean is calculated along
            all element(s) of ``axis`` . ``axis`` or element(s) of ``axis``
            should be in range [-D, D), where D is the dimensions of ``x`` . If
            ``axis`` or element(s) of ``axis`` is less than 0, it works the
            same way as :math:`axis + D` . If ``axis`` is None, nanmean is
            calculated over all elements of ``x``. Default is None.
        keepdim (bool, optional): Whether to reserve the reduced dimension(s)
            in the output Tensor. If ``keepdim`` is True, the dimensions of
            the output Tensor is the same as ``x`` except in the reduced
            dimensions(it is of size 1 in this case). Otherwise, the shape of
            the output Tensor is squeezed in ``axis`` . Default is False.
        name (str, optional): Name for the operation (optional, default is None).
            For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor, results of arithmetic mean along ``axis`` of ``x``, with the same data
        type as ``x``.

    Examples:

        .. code-block:: python
            :name: code-example1

            import paddle
            # x is a 2-D Tensor:
            x = paddle.to_tensor([[float('nan'), 0.3, 0.5, 0.9],
                                  [0.1, 0.2, float('-nan'), 0.7]])
            out1 = paddle.nanmean(x)
            # [0.44999996]
            out2 = paddle.nanmean(x, axis=0)
            # [0.1, 0.25, 0.5, 0.79999995]
            out3 = paddle.nanmean(x, axis=0, keepdim=True)
            # [[0.1, 0.25, 0.5, 0.79999995]]
            out4 = paddle.nanmean(x, axis=1)
            # [0.56666666 0.33333334]
            out5 = paddle.nanmean(x, axis=1, keepdim=True)
            # [[0.56666666]
            #  [0.33333334]]

            # y is a 3-D Tensor:
            y = paddle.to_tensor([[[1, float('nan')], [3, 4]],
                                   [[5, 6], [float('-nan'), 8]]])
            out6 = paddle.nanmean(y, axis=[1, 2])
            # [2.66666675, 6.33333349]
            out7 = paddle.nanmean(y, axis=[0, 1])
            # [3., 6.]
    x/input)rZ   rY   r?   r@   nanmeanNzaxis/dim)r   r   r   r   rN   )rd   r   r   r   rt   r   r   r   r   r   r   ZastyperP   )r>   r   r   rN   ZcntrR   rR   rS   r   7  s   
7"r   c                 C   s   |dur2t |tr|g}t| j}tt|D ]}t || tr-|| |k r-|| | ks1tdqt| d}t|d}tj||||dS )a  
    Counts the number of non-zero values in the tensor x along the specified axis.

    Args:
        x (Tensor): An N-D Tensor, the data type is bool, float16, float32, float64, int32 or int64.
        axis (int|list|tuple, optional): The dimensions along which the sum is performed. If
            :attr:`None`, sum all elements of :attr:`x` and return a
            Tensor with a single element, otherwise must be in the
            range :math:`[-rank(x), rank(x))`. If :math:`axis[i] < 0`,
            the dimension to reduce is :math:`rank + axis[i]`.
        keepdim (bool, optional): Whether to reserve the reduced dimension in the
            output Tensor. The result Tensor will have one fewer dimension
            than the :attr:`x` unless :attr:`keepdim` is true, default
            value is False.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: Results of count operation on the specified axis of input Tensor `x`, it's data type is `'int64'`.

    Examples:

        .. code-block:: python

            import paddle
            # x is a 2-D Tensor:
            x = paddle.to_tensor([[0., 1.1, 1.2], [0., 0., 1.3], [0., 0., 0.]])
            out1 = paddle.count_nonzero(x)
            # [3]
            out2 = paddle.count_nonzero(x, axis=0)
            # [0, 1, 2]
            out3 = paddle.count_nonzero(x, axis=0, keepdim=True)
            # [[0, 1, 2]]
            out4 = paddle.count_nonzero(x, axis=1)
            # [2, 1, 0]
            out5 = paddle.count_nonzero(x, axis=1, keepdim=True)
            #[[2],
            # [1],
            # [0]]

            # y is a 3-D Tensor:
            y = paddle.to_tensor([[[0., 1.1, 1.2], [0., 0., 1.3], [0., 0., 0.]],
                                  [[0., 2.5, 2.6], [0., 0., 2.4], [2.1, 2.2, 2.3]]])
            out6 = paddle.count_nonzero(y, axis=[1, 2])
            # [3, 6]
            out7 = paddle.count_nonzero(y, axis=[0, 1])
            # [1, 3, 5]
    NzQAxis should be None, int, or a list, element should in range [-rank(x), rank(x)).r   r]   r   )	rd   r   ru   r   rangerv   r   r	   r   )r>   r   r   rN   dimsiZbool_tensorZ
int_tensorrR   rR   rS   count_nonzeroz  s   2

(r   )r   c                 C   s  t  r"t| tr| g} | D ]}| st| dd  S qt| S t r4t| tr-| g} t| ddS t	di t
 }t| dtttfd t| tsPt| tret| dkrd| D ]}t|dg dd qXn	t| dg dd |j|dd}|jdd	| id
|iddid |S )a  
    Sum one or more Tensor of the input.
    
    For example:

    .. code-block:: text
    
        Case 1:

            Input:
                input.shape = [2, 3]
                input = [[1, 2, 3],
                         [4, 5, 6]]

            Output:
                output.shape = [2, 3]
                output = [[1, 2, 3],
                          [4, 5, 6]]

        Case 2:
       
            Input:
                First input:
                    input1.shape = [2, 3]
                    Input1 = [[1, 2, 3],
                              [4, 5, 6]]

                The second input:
                    input2.shape = [2, 3]
                    input2 = [[7, 8, 9],
                              [10, 11, 12]]

                Output:
                    output.shape = [2, 3]
                    output = [[8, 10, 12],
                              [14, 16, 18]]

    Args:
        inputs (Tensor|list[Tensor]|tuple[Tensor]):  A Tensor or a list/tuple of Tensors. The shape and data type of the list/tuple elements should be consistent.
            Input can be multi-dimensional Tensor, and data types can be: float32, float64, int32, int64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor, the sum of input :math:`inputs` , its shape and data types are consistent with :math:`inputs`.

    Examples:
        .. code-block:: python

            import paddle

            input0 = paddle.to_tensor([[1, 2, 3], [4, 5, 6]], dtype='float32')
            input1 = paddle.to_tensor([[7, 8, 9], [10, 11, 12]], dtype='float32')
            output = paddle.add_n([input0, input1])
            # [[8., 10., 12.], 
            #  [14., 16., 18.]]
    r   Fadd_nrG   r   rY   r?   r@   r\   r]   r^   r   rB   rD   r_   N)r   )r   rd   r   Zis_denser<   r   r;   r   r   r   rI   r   r   rt   ru   r   rK   rJ   rL   )rG   rN   r>   rO   inputrQ   rR   rR   rS   r     sD   :


r   c                 C   sv   t  rt| S t rt| S d| i}i }tdi t }t| dg dd |j| j	d}|j
d||d|id |S )	a  
    This API is used to returns a new tensor with the truncated integer values of input.
    
    Args:
        input (Tensor): The input tensor, it's data type should be int32, int64, float32, float64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.
    
    Returns:
        Tensor: The output Tensor of trunc.
    
    Examples:
        .. code-block:: python

            import paddle

            input = paddle.rand([2,2],'float32')
            print(input)
            # Tensor(shape=[2, 2], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #         [[0.02331470, 0.42374918],
            #         [0.79647720, 0.74970269]])

            output = paddle.trunc(input)
            print(output)
            # Tensor(shape=[2, 2], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #         [[0., 0.],
            #         [0., 0.]]))
    rB   truncr\   r]   r?   r@   r^   rD   rF   rG   r`   rH   Nr   )r   r;   r   r   r<   r   rI   r   rK   rP   rL   )r   rN   rG   r`   rO   rQ   rR   rR   rS   r     s   

r   c                 C   sx   t  rt| |ddS t rt| |S dd }|| | tdi t }|j	| j
d}|jd| |dd|id	 |S )ap  

    Applies matrix multiplication to two tensors.

    Currently, the input tensors' rank can be any, but when the rank of any
    inputs is bigger than 3, this two inputs' rank should be equal.


    Also note that if the raw tensor :math:`x` or :math:`mat2` is rank-1 and
    nontransposed, the prepended or appended dimension :math:`1` will be
    removed after matrix multiplication.

    Args:
        input (Tensor): The input tensor which is a Tensor.
        mat2 (Tensor): The input tensor which is a Tensor.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: The product Tensor.

    ::

        * example 1:

        input: [B, ..., M, K], mat2: [B, ..., K, N]
        out: [B, ..., M, N]

        * example 2:

        input: [B, M, K], mat2: [B, K, N]
        out: [B, M, N]

        * example 3:

        input: [B, M, K], mat2: [K, N]
        out: [B, M, N]

        * example 4:

        input: [M, K], mat2: [K, N]
        out: [M, N]

        * example 5:

        input: [B, M, K], mat2: [K]
        out: [B, M]

        * example 6:

        input: [K], mat2: [K]
        out: [1]

    Examples:
        .. code-block:: python

            import paddle
            input = paddle.arange(1, 7).reshape((3, 2)).astype('float32')
            mat2 = paddle.arange(1, 9).reshape((2, 4)).astype('float32')
            out = paddle.mm(input, mat2)
            print(out)
            #        [[11., 14., 17., 20.],
            #         [23., 30., 37., 44.],
            #         [35., 46., 57., 68.]])


    Fc           	      S   s  | |d}|  D ]\}}t||g dd q	t| j}t|j}t|dkr,dg| }t|dkr7|dg }|d |d krS|d dksS|d dksStd||f t|dkrt|dkrt|d d D ]#\}}|d	k su|| d	k rvqg||| krtd
||||f qgd S d S d S )Nr>   r   rn   mmr   r|   zAfter performing an optional transpose, Input X's width should be equal to Y's width for multiplication prerequisites. But received X's shape: %s, Y's shape: %s
r   r   zWhen the matrix is larger than 2 dimensions, the higher dimensional values of the two matrices need to be equal. But received x_shape[%d] != y_shape[%d]. X's shape: %s, Y's shape: %s.
)itemsr   rt   r   ru   rv   rw   )	r>   r   	var_namesrN   valx_shapey_shaper   Zdim_xrR   rR   rS   __check_input  s>   





zmm.<locals>.__check_inputr   r^   	matmul_v2r   rD   rE   N)r   )r   r;   matmulr   in_dynamic_moder<   r   r   rI   rK   rP   rL   )r   Zmat2rN   r   rO   rQ   rR   rR   rS   r   G  s   C
!r   c              	   C   s  | j }|j }|j }t|t|  krdks n td|||d |d kr0td||t|dkr||d |d krd|d dkrMtd|d |d |d krd|d dkrdtd|d |d |d kr{|d dkr{td|d n%t|dkr|d |d dfvrtd||d |d ntd	|t rt| ||||S t rt| ||d
|d|}	|	S | ||d}
||d}t	di t
 }t| dddgd t|dddgd t|dddgd |j|jd}	|jd|
|d|	id |	S )a  
    **addmm**

    Perform matrix multiplication for input $x$ and $y$.
    $input$ is added to the final result.
    The equation is:

    ..  math::
        Out = alpha * x * y + beta * input

    $Input$, $x$ and $y$ can carry the LoD (Level of Details) information, or not. But the output only shares the LoD information with input $input$.

    Args:
        input (Tensor): The input Tensor to be added to the final result.
        x (Tensor): The first input Tensor for matrix multiplication.
        y (Tensor): The second input Tensor for matrix multiplication.
        beta (float, optional): Coefficient of $input$, default is 1.
        alpha (float, optional): Coefficient of $x*y$, default is 1.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: The output Tensor of addmm.

    Examples:
        ..  code-block:: python
            
            import paddle

            x = paddle.ones([2,2])
            y = paddle.ones([2,2])
            input = paddle.ones([2,2])

            out = paddle.addmm( input=input, x=x, y=y, beta=0.5, alpha=5.0 )

            print(out)
            # [[10.5 10.5]
            # [10.5 10.5]]
    r   zJThe dimention of x, y should be 2 but receive x's shape: {}, y's shape: {}r   r   zpThe input Variable x's width must be equal with Variable y' height. But received x's shape = {}, y's shape = {}.zgWhen x's dimension[0] is not equal with input's dimension[0], input's dimension[0] must be 1 but got {}zgWhen y's dimension[1] is not equal with input's dimension[1], input's dimension[1] must be 1 but got {}zQThe input's shape: {} is not broadcastable with [x.shape[0], y.shape[1]]: [{},{}]zEThe dimention of input should be 2 or 1 but receive input's shape: {}AlphaBeta)InputrB   r   )r   r   addmmr   r?   r@   rB   r   r^   rD   r   N)r   )r   ru   rv   r   r   r;   r   r   r<   r   rI   r   rK   rP   rL   )r   r>   r   betaalpharN   input_shaper   r   rQ   rG   r`   rO   rR   rR   rS   r     sL   '
r   c           	   	   C   s   | j }t| dddgd |t|k std|t|||dks;|dt| ks5td|dt| |t| }t rHt| |||}|S t rXt	| d	|d
|d|}|S d| i}|||d}t
di t }|j| jd}|jd||d|id |S )a  
    **renorm**

    This operator is used to calculate the p-norm along the axis,
    suppose the input-shape on axis dimension has the value of T, then
    the tensor is split into T parts, the p-norm should be calculated for each
    part, if the p-norm for part i is larger than max-norm, then each element 
    in part i should be re-normalized at the same scale so that part-i' p-norm equals
    max-norm exactly, otherwise part-i stays unchanged.

    Args:
        x (Tensor): The input Tensor
        p (float): The power of the norm operation.
        axis (int): the dimension to slice the tensor.
        max-norm (float): the maximal norm limit.

    Returns:
        Tensor: the renorm Tensor.

    Examples:
        ..  code-block:: python
            
            import paddle
            input = [[[2.0,2,-2],[3,0.3,3]],[[2,-8,2],[3.1,3.7,3]]]
            x = paddle.to_tensor(input,dtype='float32')
            y = paddle.renorm(x, 1.0, 2, 2.05)
            print(y)        
    #        [[[ 0.40594056,  0.29285714, -0.41000000],
    #          [ 0.60891086,  0.04392857,  0.61500001]],
    #         [[ 0.40594056, -1.17142856,  0.41000000],
    #          [ 0.62920785,  0.54178572,  0.61500001]]])
    
    r>   r?   r@   renormz6the axis:{} should be less then the shape's size {}:{}r   r|   zAthe axis:{} should not be less than -1 * length of input_shape:{}pr   max_normrB   )r   r   r   r^   rD   r   N)r   )r   r   ru   rv   r   r   r;   r   r   r<   r   rI   rK   rP   rL   )	r>   r   r   r   r   rQ   rG   r`   rO   rR   rR   rS   r     s,   "r   c           	         s  | j dks
|j dkrt| |S | j |jt dd tdd  }t|dkr.dg}| d d f}|dd f}t rOt||j	dd|S t
 r]t||j	|S  fdd}||| tdi t }|j|jd	}|jd
||j	dd|id ||S )a  

    Inner product of two input Tensor.
    
    Ordinary inner product for 1-D Tensors, in higher dimensions a sum product over the last axes.

    Args:
        x (Tensor): An N-D Tensor or a Scalar Tensor. If its not a scalar Tensor, its last dimensions must match y's.
        y (Tensor): An N-D Tensor or a Scalar Tensor. If its not a scalar Tensor, its last dimensions must match x's.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: The inner-product Tensor, the output shape is x.shape[:-1] + y.shape[:-1].

    Examples:
        .. code-block:: python

            import paddle
            x = paddle.arange(1, 7).reshape((2, 3)).astype('float32')
            y = paddle.arange(1, 10).reshape((3, 3)).astype('float32')
            out = paddle.inner(x, y)
            print(out)
            #        ([[14, 32, 50],
            #         [32, 77, 122]])


    r   Nr|   r   Fc                    s   | |d}|  D ]\}}t||g dd q	t }t}|d |d kr;|d dks=|d dks?td||f d S d S d S )Nr   rn   innerr|   zAfter performing an optional transpose, Input X's last dim should be equal to Y's last dim for multiplication prerequisites. But received X's shape: %s, Y's shape: %s
)r   r   rt   rv   )r>   r   r   rN   r   r   r   ZxshapeZyshaperR   rS   r   v  s    
zinner.<locals>.__check_inputr   r^   r   r   rD   rE   )r   )sizer   r   rt   ru   reshaper   r;   r   Tr   r   r<   r   r   rI   rK   rP   rL   )	r>   r   rN   Zdstshapenxnyr   rO   rQ   rR   r   rS   r   J  s0   
 

r   c                 C   s   |  d}| d}t rt||ddS t rt||S dd }||| tdi t	 }|j
|jd}|jd||d	d
|id |S )a  

    Outer product of two Tensors.

    Input is flattened if not already 1-dimensional.

    Args:
        x (Tensor): An N-D Tensor or a Scalar Tensor. 
        y (Tensor): An N-D Tensor or a Scalar Tensor. 
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: The outer-product Tensor.

    Examples:
        .. code-block:: python

            import paddle
            x = paddle.arange(1, 4).astype('float32')
            y = paddle.arange(1, 6).astype('float32')
            out = paddle.outer(x, y)
            print(out)
            #        ([[1, 2, 3, 4, 5],
            #         [2, 4, 6, 8, 10],
            #         [3, 6, 9, 12, 15]])


    )r|   r   )r   r|   Fc                 S   s2   | |d}|  D ]\}}t||g dd q	d S )Nr   rn   r   )r   r   )r>   r   r   rN   r   rR   rR   rS   r     s   
zouter.<locals>.__check_inputouterr^   r   r   rD   rE   N)r   )r   r   r;   r   r   r   r<   r   r   rI   rK   rP   rL   )r>   r   rN   r   r   r   rO   rQ   rR   rR   rS   r     s"   


r   c              	   C   s   t |tr|g}|du st|dkst|t| jkrdnd}|du s)t|dkr,dg}t r@|r8tt| j}t| |||S t rNt	| d|d|d|S t
| dd	d
gd tdi t }|||d}|| j}|jdd| id|i|d |S )a
  
    Calculates the log of the sum of exponentials of ``x`` along ``axis`` .

    .. math::
       logsumexp(x) = \log\sum exp(x)

    Args:
        x (Tensor): The input Tensor with data type float32 or float64, which 
            have no more than 4 dimensions.
        axis (int|list|tuple, optional): The axis along which to perform
            logsumexp calculations. ``axis`` should be int, list(int) or
            tuple(int). If ``axis`` is a list/tuple of dimension(s), logsumexp
            is calculated along all element(s) of ``axis`` . ``axis`` or
            element(s) of ``axis`` should be in range [-D, D), where D is the
            dimensions of ``x`` . If ``axis`` or element(s) of ``axis`` is
            less than 0, it works the same way as :math:`axis + D` . If
            ``axis`` is None, logsumexp is calculated along all elements of
            ``x``. Default is None.
        keepdim (bool, optional): Whether to reserve the reduced dimension(s)
            in the output Tensor. If ``keep_dim`` is True, the dimensions of
            the output Tensor is the same as ``x`` except in the reduced
            dimensions(it is of size 1 in this case). Otherwise, the shape of
            the output Tensor is squeezed in ``axis`` . Default is False.
        name (str, optional): Name for the operation (optional, default is None).
            For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor, results of logsumexp along ``axis`` of ``x``, with the same data
        type as ``x``.

    Examples:

    .. code-block:: python

        import paddle

        x = paddle.to_tensor([[-1.5, 0., 2.], [3., 1.2, -2.4]])
        out1 = paddle.logsumexp(x) # [3.4691226]
        out2 = paddle.logsumexp(x, 1) # [2.15317821, 3.15684602]

    Nr   TFr   r   r   r>   r?   r@   	logsumexp)r   r   r   rB   rD   r_   )r   )rd   r   ru   r   r   r   r;   r   r   r<   r   r   rI   rK   rP   rL   )r>   r   r   rN   r   rO   r`   rQ   rR   rR   rS   r     s6   
*r   c                 C   sp   t  rt| S t rt| S dd }||  td	i t }|j| j	d}|j
dd| gid|gid |S )
a  
    Takes the inverse of the square matrix. A square matrix is a matrix with
    the same number of rows and columns. The input can be a square matrix
    (2-D Tensor) or batches of square matrices.

    Args:
        x (Tensor): The input tensor. The last two
            dimensions should be equal. When the number of dimensions is
            greater than 2, it is treated as batches of square matrix. The data
            type can be float32 and float64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: A Tensor holds the inverse of x. The shape and data type
                        is the same as x.

    Examples:
        .. code-block:: python

            import paddle

            mat = paddle.to_tensor([[2, 0], [0, 2]], dtype='float32')
            inv = paddle.inverse(mat)
            print(inv) # [[0.5, 0], [0, 0.5]]

    c                 S   s<   t | dddgd t| jdk rtdt| j| jf d S )Nr>   r?   r@   inverser   z}The input of inverse is expected to be a Tensor whose number of dimensions is no less than 2. But reviced: %d, x's shape: %s.)r   ru   r   rv   )r>   rR   rR   rS   _check_input+  s   zinverse.<locals>._check_inputr   r^   r   OutputrE   N)r   )r   r;   r   r   r   r<   r   rI   rK   rP   rL   )r>   rN   r   rO   rQ   rR   rR   rS   r     s   

r   c                 C   sv   | dur%t | ts%t | trt| } nt | tr| g} n	tdt| | dks-| g kr/dnd}| dkr7g } || fS )w
    Internal function for max, min, amax and amin. 
    It computes the attribute reduce_all value based on axis.
    N<The type of axis must be int, list or tuple, but received {}TFrd   rt   r   r   r   r   rF   r   r   rR   rR   rS   _get_reduce_axis:  s   


r  c                 C   s   t | tr	d| fS t| S )NF)rd   r   r  r   rR   rR   rS   _get_reduce_axis_with_tensorL  s   
r  c                 C   s   | dur%t | ts%t | trt| } nt | tr| g} n	tdt| | dks-| g kr/dnd}| dkr;| g kr;| ndg} || fS )r   Nr   TFr   r   r   rR   rR   rS   _get_reduce_all_valueQ  s   


r  c              	   C      t |\}}t rt| ||S t rt| d|d|d|S tdi t }t	| dg dd t
|ts>t|r>t|}|j| jd}|jdd	| id
|i|||dd |S )a  

    Computes the maximum of tensor elements over the given axis.

    Note:
        The difference between max and amax is: If there are multiple maximum elements,
        amax evenly distributes gradient between these equal values, 
        while max propagates gradient to all of them.


    Args:
        x (Tensor): A tensor, the data type is float32, float64, int32, int64.
        axis (int|list|tuple, optional): The axis along which the maximum is computed.
            If :attr:`None`, compute the maximum over all elements of
            `x` and return a Tensor with a single element,
            otherwise must be in the range :math:`[-x.ndim(x), x.ndim(x))`.
            If :math:`axis[i] < 0`, the axis to reduce is :math:`x.ndim + axis[i]`.
        keepdim (bool, optional): Whether to reserve the reduced dimension in the
            output Tensor. The result tensor will have one fewer dimension
            than the `x` unless :attr:`keepdim` is true, default
            value is False.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor, results of maximum on the specified axis of input tensor,
        it's data type is the same as `x`.

    Examples:
        .. code-block:: python

            import paddle

            # data_x is a Tensor with shape [2, 4]
            # the axis is a int element
            x = paddle.to_tensor([[0.2, 0.3, 0.5, 0.9],
                                  [0.1, 0.2, 0.6, 0.7]], 
                                 dtype='float64', stop_gradient=False)
            result1 = paddle.max(x)
            result1.backward()
            print(result1, x.grad) 
            #[0.9], [[0., 0., 0., 1.], [0., 0., 0., 0.]]

            x.clear_grad()
            result2 = paddle.max(x, axis=0)
            result2.backward()
            print(result2, x.grad) 
            #[0.2, 0.3, 0.6, 0.9], [[1., 1., 0., 1.], [0., 0., 1., 0.]]

            x.clear_grad()
            result3 = paddle.max(x, axis=-1)
            result3.backward()
            print(result3, x.grad) 
            #[0.9, 0.7], [[0., 0., 0., 1.], [0., 0., 0., 1.]]

            x.clear_grad()
            result4 = paddle.max(x, axis=1, keepdim=True)
            result4.backward()
            print(result4, x.grad) 
            #[[0.9], [0.7]], [[0., 0., 0., 1.], [0., 0., 0., 1.]]

            # data_y is a Tensor with shape [2, 2, 2]
            # the axis is list 
            y = paddle.to_tensor([[[1.0, 2.0], [3.0, 4.0]],
                                  [[5.0, 6.0], [7.0, 8.0]]],
                                 dtype='float64', stop_gradient=False)
            result5 = paddle.max(y, axis=[1, 2])
            result5.backward()
            print(result5, y.grad) 
            #[4., 8.], [[[0., 0.], [0., 1.]], [[0., 0.], [0., 1.]]]

            y.clear_grad()
            result6 = paddle.max(y, axis=[0, 1])
            result6.backward()
            print(result6, y.grad) 
            #[7., 8.], [[[0., 0.], [0., 0.]], [[0., 0.], [1., 1.]]]
    r   r   r   maxr>   rr   r^   
reduce_maxrB   rD   r   r_   N)r  )r  r   r;   r  r   r<   r  r   rI   r   rd   r   r   r   r   rK   rP   rL   r>   r   r   rN   r   rO   rQ   rR   rR   rS   r  c  s4   N
	r  c              	   C   r  )a!  

    Computes the minimum of tensor elements over the given axis

    Note:
        The difference between min and amin is: If there are multiple minimum elements,
        amin evenly distributes gradient between these equal values, 
        while min propagates gradient to all of them.

    Args:
        x (Tensor): A tensor, the data type is float32, float64, int32, int64.
        axis (int|list|tuple, optional): The axis along which the minimum is computed.
            If :attr:`None`, compute the minimum over all elements of
            `x` and return a Tensor with a single element,
            otherwise must be in the range :math:`[-x.ndim, x.ndim)`.
            If :math:`axis[i] < 0`, the axis to reduce is :math:`x.ndim + axis[i]`.
        keepdim (bool, optional): Whether to reserve the reduced dimension in the
            output Tensor. The result tensor will have one fewer dimension
            than the `x` unless :attr:`keepdim` is true, default
            value is False.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor, results of minimum on the specified axis of input tensor,
        it's data type is the same as input's Tensor.

    Examples:
        .. code-block:: python

            import paddle

            # data_x is a Tensor with shape [2, 4]
            # the axis is a int element
            x = paddle.to_tensor([[0.2, 0.3, 0.5, 0.9],
                                  [0.1, 0.2, 0.6, 0.7]], 
                                 dtype='float64', stop_gradient=False)
            result1 = paddle.min(x)
            result1.backward()
            print(result1, x.grad) 
            #[0.1], [[0., 0., 0., 0.], [1., 0., 0., 0.]]

            x.clear_grad()
            result2 = paddle.min(x, axis=0)
            result2.backward()
            print(result2, x.grad) 
            #[0.1, 0.2, 0.5, 0.7], [[0., 0., 1., 0.], [1., 1., 0., 1.]]

            x.clear_grad()
            result3 = paddle.min(x, axis=-1)
            result3.backward()
            print(result3, x.grad) 
            #[0.2, 0.1], [[1., 0., 0., 0.], [1., 0., 0., 0.]]

            x.clear_grad()
            result4 = paddle.min(x, axis=1, keepdim=True)
            result4.backward()
            print(result4, x.grad) 
            #[[0.2], [0.1]], [[1., 0., 0., 0.], [1., 0., 0., 0.]]

            # data_y is a Tensor with shape [2, 2, 2]
            # the axis is list 
            y = paddle.to_tensor([[[1.0, 2.0], [3.0, 4.0]],
                                  [[5.0, 6.0], [7.0, 8.0]]],
                                 dtype='float64', stop_gradient=False)
            result5 = paddle.min(y, axis=[1, 2])
            result5.backward()
            print(result5, y.grad) 
            #[1., 5.], [[[1., 0.], [0., 0.]], [[1., 0.], [0., 0.]]]

            y.clear_grad()
            result6 = paddle.min(y, axis=[0, 1])
            result6.backward()
            print(result6, y.grad) 
            #[1., 2.], [[[1., 1.], [0., 0.]], [[0., 0.], [0., 0.]]]
    r   r   r   minr>   rr   r^   
reduce_minrB   rD   r   r_   N)r	  )r  r   r;   r	  r   r<   r
  r   rI   r   rd   r   r   r   r   rK   rP   rL   r  rR   rR   rS   r	    s4   M
	r	  c              	   C      t |\}}t rt| ||S t rt| d|d|d|S tdi t }t	| dg dd |j
| jd}|jdd	| id
|i|||dd |S )a  
    Computes the maximum of tensor elements over the given axis.

    Note:
        The difference between max and amax is: If there are multiple maximum elements,
        amax evenly distributes gradient between these equal values, 
        while max propagates gradient to all of them.

    Args:
        x (Tensor): A tensor, the data type is float32, float64, int32, int64,
            the dimension is no more than 4.
        axis (int|list|tuple, optional): The axis along which the maximum is computed.
            If :attr:`None`, compute the maximum over all elements of
            `x` and return a Tensor with a single element,
            otherwise must be in the range :math:`[-x.ndim(x), x.ndim(x))`.
            If :math:`axis[i] < 0`, the axis to reduce is :math:`x.ndim + axis[i]`.
        keepdim (bool, optional): Whether to reserve the reduced dimension in the
            output Tensor. The result tensor will have one fewer dimension
            than the `x` unless :attr:`keepdim` is true, default
            value is False.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor, results of maximum on the specified axis of input tensor,
        it's data type is the same as `x`.

    Examples:
        .. code-block:: python

            import paddle
            # data_x is a Tensor with shape [2, 4] with multiple maximum elements
            # the axis is a int element

            x = paddle.to_tensor([[0.1, 0.9, 0.9, 0.9],
                                  [0.9, 0.9, 0.6, 0.7]], 
                                 dtype='float64', stop_gradient=False)
            # There are 5 maximum elements: 
            # 1) amax evenly distributes gradient between these equal values, 
            #    thus the corresponding gradients are 1/5=0.2;
            # 2) while max propagates gradient to all of them, 
            #    thus the corresponding gradient are 1.
            result1 = paddle.amax(x)
            result1.backward()
            print(result1, x.grad) 
            #[0.9], [[0., 0.2, 0.2, 0.2], [0.2, 0.2, 0., 0.]]

            x.clear_grad()
            result1_max = paddle.max(x)
            result1_max.backward()
            print(result1_max, x.grad) 
            #[0.9], [[0., 1.0, 1.0, 1.0], [1.0, 1.0, 0., 0.]]

            ###############################

            x.clear_grad()
            result2 = paddle.amax(x, axis=0)
            result2.backward()
            print(result2, x.grad) 
            #[0.9, 0.9, 0.9, 0.9], [[0., 0.5, 1., 1.], [1., 0.5, 0., 0.]]

            x.clear_grad()
            result3 = paddle.amax(x, axis=-1)
            result3.backward()
            print(result3, x.grad) 
            #[0.9, 0.9], [[0., 0.3333, 0.3333, 0.3333], [0.5, 0.5, 0., 0.]]

            x.clear_grad()
            result4 = paddle.amax(x, axis=1, keepdim=True)
            result4.backward()
            print(result4, x.grad) 
            #[[0.9], [0.9]], [[0., 0.3333, 0.3333, 0.3333.], [0.5, 0.5, 0., 0.]]

            # data_y is a Tensor with shape [2, 2, 2]
            # the axis is list 
            y = paddle.to_tensor([[[0.1, 0.9], [0.9, 0.9]],
                                  [[0.9, 0.9], [0.6, 0.7]]],
                                 dtype='float64', stop_gradient=False)
            result5 = paddle.amax(y, axis=[1, 2])
            result5.backward()
            print(result5, y.grad) 
            #[0.9., 0.9], [[[0., 0.3333], [0.3333, 0.3333]], [[0.5, 0.5], [0., 1.]]]

            y.clear_grad()
            result6 = paddle.amax(y, axis=[0, 1])
            result6.backward()
            print(result6, y.grad) 
            #[0.9., 0.9], [[[0., 0.3333], [0.5, 0.3333]], [[0.5, 0.3333], [1., 1.]]]
    r   r   r   amaxr>   rr   r^   reduce_amaxrB   rD   r   r_   N)r  )r  r   r;   r  r   r<   r  r   rI   r   rK   rP   rL   r  rR   rR   rS   r  3	  s,   Z	r  c              	   C   r  )a  

    Computes the minimum of tensor elements over the given axis

    Note:
        The difference between min and amin is: If there are multiple minimum elements,
        amin evenly distributes gradient between these equal values, 
        while min propagates gradient to all of them.

    Args:
        x (Tensor): A tensor, the data type is float32, float64, int32, int64, 
            the dimension is no more than 4.
        axis (int|list|tuple, optional): The axis along which the minimum is computed.
            If :attr:`None`, compute the minimum over all elements of
            `x` and return a Tensor with a single element,
            otherwise must be in the range :math:`[-x.ndim, x.ndim)`.
            If :math:`axis[i] < 0`, the axis to reduce is :math:`x.ndim + axis[i]`.
        keepdim (bool, optional): Whether to reserve the reduced dimension in the
            output Tensor. The result tensor will have one fewer dimension
            than the `x` unless :attr:`keepdim` is true, default
            value is False.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor, results of minimum on the specified axis of input tensor,
        it's data type is the same as input's Tensor.

    Examples:
        .. code-block:: python

            import paddle
            # data_x is a Tensor with shape [2, 4] with multiple minimum elements
            # the axis is a int element

            x = paddle.to_tensor([[0.2, 0.1, 0.1, 0.1],
                                  [0.1, 0.1, 0.6, 0.7]], 
                                 dtype='float64', stop_gradient=False)
            # There are 5 minimum elements: 
            # 1) amin evenly distributes gradient between these equal values, 
            #    thus the corresponding gradients are 1/5=0.2;
            # 2) while min propagates gradient to all of them, 
            #    thus the corresponding gradient are 1.
            result1 = paddle.amin(x)
            result1.backward()
            print(result1, x.grad) 
            #[0.1], [[0., 0.2, 0.2, 0.2], [0.2, 0.2, 0., 0.]]

            x.clear_grad()
            result1_min = paddle.min(x)
            result1_min.backward()
            print(result1_min, x.grad) 
            #[0.1], [[0., 1.0, 1.0, 1.0], [1.0, 1.0, 0., 0.]]

            ###############################

            x.clear_grad()
            result2 = paddle.amin(x, axis=0)
            result2.backward()
            print(result2, x.grad) 
            #[0.1, 0.1, 0.1, 0.1], [[0., 0.5, 1., 1.], [1., 0.5, 0., 0.]]

            x.clear_grad()
            result3 = paddle.amin(x, axis=-1)
            result3.backward()
            print(result3, x.grad) 
            #[0.1, 0.1], [[0., 0.3333, 0.3333, 0.3333], [0.5, 0.5, 0., 0.]]

            x.clear_grad()
            result4 = paddle.amin(x, axis=1, keepdim=True)
            result4.backward()
            print(result4, x.grad) 
            #[[0.1], [0.1]], [[0., 0.3333, 0.3333, 0.3333.], [0.5, 0.5, 0., 0.]]

            # data_y is a Tensor with shape [2, 2, 2]
            # the axis is list 
            y = paddle.to_tensor([[[0.2, 0.1], [0.1, 0.1]],
                                  [[0.1, 0.1], [0.6, 0.7]]],
                                 dtype='float64', stop_gradient=False)
            result5 = paddle.amin(y, axis=[1, 2])
            result5.backward()
            print(result5, y.grad) 
            #[0.1., 0.1], [[[0., 0.3333], [0.3333, 0.3333]], [[0.5, 0.5], [0., 1.]]]

            y.clear_grad()
            result6 = paddle.amin(y, axis=[0, 1])
            result6.backward()
            print(result6, y.grad) 
            #[0.1., 0.1], [[[0., 0.3333], [0.5, 0.3333]], [[0.5, 0.3333], [1., 1.]]]
    r   r   r   aminr>   rr   r^   reduce_aminrB   rD   r   r_   N)r  )r  r   r;   r  r   r<   r  r   rI   r   rK   rP   rL   r  rR   rR   rS   r  	  s,   [	r  c                 C   r=   )a  
    Calculates the natural log of the given input tensor, element-wise.

    .. math::
        Out = \ln(x+1)

    Args:
        x (Tensor): Input Tensor. Must be one of the following types: float32, float64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.
        
    Returns:
        Tensor, the natural log of the input Tensor computed element-wise.

    Examples:
        .. code-block:: python

            import paddle

            data = paddle.to_tensor([[0], [1]], dtype='float32')
            res = paddle.log1p(data)
            # [[0.], [0.6931472]]
    r>   r?   r@   log1prB   rC   rD   rE   N)r  )r   r;   r  r   r<   r   r   rI   rJ   rK   rL   rM   rR   rR   rS   r  
  s   



r  c                 C   ~   t  rt| S t rt| S t| dg dd d| gi}td	i t }|jdd}|	|}|j
dd| id|id |S )
aO  
    Calculates the log to the base 2 of the given input tensor, element-wise.

    .. math::

        Out = \log_2x

    Args:
        x (Tensor): Input tensor must be one of the following types: float32, float64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.


    Returns:
        Tensor: The log to the base 2 of the input Tensor computed element-wise.

    Examples:

        .. code-block:: python
        
            import paddle

            # example 1: x is a float
            x_i = paddle.to_tensor([[1.0], [2.0]])
            res = paddle.log2(x_i) # [[0.], [1.0]]

            # example 2: x is float32
            x_i = paddle.full(shape=[1], fill_value=2, dtype='float32')
            paddle.to_tensor(x_i)
            res = paddle.log2(x_i)
            print(res) # [1.0]

            # example 3: x is float64
            x_i = paddle.full(shape=[1], fill_value=2, dtype='float64')
            paddle.to_tensor(x_i)
            res = paddle.log2(x_i)
            print(res) # [1.0]
    r>   rn   log2rB   rC   rD   rE   N)r  )r   r;   r  r   r<   r   r   rI   rJ   rK   rL   rM   rR   rR   rS   r  :
     &



r  c                 C   r  )
aY  
    Calculates the log to the base 10 of the given input tensor, element-wise.

    .. math::

        Out = \log_10_x

    Args:
        x (Tensor): Input tensor must be one of the following types: float32, float64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.


    Returns:
        Tensor: The log to the base 10 of the input Tensor computed element-wise.

    Examples:

        .. code-block:: python
        
            import paddle

            # example 1: x is a float
            x_i = paddle.to_tensor([[1.0], [10.0]])
            res = paddle.log10(x_i) # [[0.], [1.0]]

            # example 2: x is float32
            x_i = paddle.full(shape=[1], fill_value=10, dtype='float32')
            paddle.to_tensor(x_i)
            res = paddle.log10(x_i)
            print(res) # [1.0]

            # example 3: x is float64
            x_i = paddle.full(shape=[1], fill_value=10, dtype='float64')
            paddle.to_tensor(x_i)
            res = paddle.log10(x_i)
            print(res) # [1.0]
    r>   rn   log10rB   rC   rD   rE   N)r  )r   r;   r  r   r<   r   r   rI   rJ   rK   rL   rM   rR   rR   rS   r  n
  r  r  c                 C   s  t | j}|dkrttjj}ttjjd }n'|dkr/ttjj}ttjjd }ntt	tj
j}tt	tj
j}t rst|trP| d}t|tr\| d}|du rb|n|}|du rj|n|}t| ||S t rt|tr| d}t|tr| d}|du r|n|}|du r|n|}t| d|d|S |durt|dtttfd	 t|trt|jdg d
d	d |durt|dtttfd	 t|trt|jdg d
d	d t| dg dd	 d| i}||d}t|trd|_||d< n	|dur||d< t|trd|_||d< n	|dur#||d< tdi t }	|	j|	dd}
|	jd	|d|
gi|d |
S )a  
    This operator clip all elements in input into the range [ min, max ] and return
    a resulting tensor as the following equation:

    .. math::

        Out = MIN(MAX(x, min), max)

    Args:
        x (Tensor): An N-D Tensor with data type float32, float64, int32 or int64.
        min (float|int|Tensor, optional): The lower bound with type ``float`` , ``int`` or a ``Tensor``
            with shape [1] and type ``int32``, ``float32``, ``float64``.
        max (float|int|Tensor, optional): The upper bound with type ``float``, ``int`` or a ``Tensor``
            with shape [1] and type ``int32``, ``float32``, ``float64``.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: A Tensor with the same data type and data shape as input.

    Examples:
        .. code-block:: python

            import paddle

            x1 = paddle.to_tensor([[1.2, 3.5], [4.5, 6.4]], 'float32')
            out1 = paddle.clip(x1, min=3.5, max=5.0)
            out2 = paddle.clip(x1, min=2.5)
            print(out1)
            # [[3.5, 3.5]
            # [4.5, 5.0]]
            print(out2)
            # [[2.5, 3.5]
            # [[4.5, 6.4]
    zpaddle.int32   zpaddle.int64l        r   Nr	  r  clip)r?   r@   r\   z+(When the type of min in clip is Variable.)z+(When the type of max in clip is Variable.)r>   rr   rB   )r	  r  TZMinZMaxr^   rD   r_   )r  )rx   rP   npZiinfor\   r	  r  r]   rb   finfor?   r   rd   r   re   rf   r;   r  r   r<   r   r   r   r   Zstop_gradientr   rI   rK   rJ   rL   )r>   r	  r  rN   Zx_dtypeZmin_Zmax_rG   r`   rO   outputrR   rR   rS   r  
  st   
$










r  c                 C   s   t ttjj}t ttjj}t|tr| 	d}t|tr*| 	d}|du r0|n|}|du r8|n|}t
 rDt| ||S t rPt| d|d|S dS )z
    Inplace version of ``clip`` API, the output Tensor will be inplaced with input ``x``.
    Please refer to :ref:`api_tensor_clip`.
    r   Nr	  r  )rb   r  r  r?   r	  r  rd   r   re   rf   r   r;   clip_r   r<   )r>   r	  r  rN   r   r   rR   rR   rS   r    s   

r  c              	   C   s   dd }t  rt| |||S t rt| d|d|d|S || ||| tdi t }|j| jd}|j	dd| gi|||d	d
|gid |S )a  

    Computes the sum along diagonals of the input tensor x.

    If ``x`` is 2D, returns the sum of diagonal.

    If ``x`` has larger dimensions, then returns an tensor of diagonals sum, diagonals be taken from
    the 2D planes specified by axis1 and axis2. By default, the 2D planes formed by the first and second axes
    of the input tensor x.

    The argument ``offset`` determines where diagonals are taken from input tensor x:

    - If offset = 0, it is the main diagonal.
    - If offset > 0, it is above the main diagonal.
    - If offset < 0, it is below the main diagonal.
    - Note that if offset is out of input's shape indicated by axis1 and axis2, 0 will be returned.

    Args:
        x (Tensor): The input tensor x. Must be at least 2-dimensional. The input data type should be float32, float64, int32, int64.
        offset (int, optional): Which diagonals in input tensor x will be taken. Default: 0 (main diagonals).
        axis1 (int, optional): The first axis with respect to take diagonal. Default: 0.
        axis2 (int, optional): The second axis with respect to take diagonal. Default: 1.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: the output data type is the same as input data type.

    Examples:
        .. code-block:: python

            import paddle

            case1 = paddle.randn([2, 3])
            case2 = paddle.randn([3, 10, 10])
            case3 = paddle.randn([3, 10, 5, 10])
            data1 = paddle.trace(case1) # data1.shape = [1]
            data2 = paddle.trace(case2, offset=1, axis1=1, axis2=2) # data2.shape = [3]
            data3 = paddle.trace(case3, offset=-3, axis1=1, axis2=-1) # data2.shape = [3, 5]
    c                 S   s   t | jdg dd t| j}t|dksJ dt| |dkr#|nt|| }|dkr/|nt|| }d|kr?|t|k sOJ dt| t|d |f d|krY|t|k siJ d	t| t|d |f ||ksuJ d
||f d S )Nr   r\   r]   rY   r?   r@   tracer   NThe x must be at least 2-dimensional, But received Input x's dimensional: %s.
r   VThe argument axis1 is out of range (expected to be in range of [%d, %d], but got %d).
r   VThe argument axis2 is out of range (expected to be in range of [%d, %d], but got %d).
Laxis1 and axis2 cannot be the same axis.But received axis1 = %d, axis2 = %d
r   rP   rt   r   ru   r>   offsetaxis1axis2r   Zaxis1_Zaxis2_rR   rR   rS   r   G  s6   

ztrace.<locals>.__check_inputr#  r$  r%  r  r^   r   r#  r$  r%  rD   r   N)r  )
r   r;   r  r   r<   r   rI   rK   rP   rL   r>   r#  r$  r%  rN   r   rO   rQ   rR   rR   rS   r    s$   (r  c              	   C   s   t  rt| |||S t rt| d|d|d|S dd }|| ||| tdi t }|j| jd}|j	dd| gi|||d	d
|gid |S )aU  
    This OP computes the diagonals of the input tensor x.

    If ``x`` is 2D, returns the diagonal.
    If ``x`` has larger dimensions, diagonals be taken from the 2D planes specified by axis1 and axis2. 
    By default, the 2D planes formed by the first and second axis of the input tensor x.

    The argument ``offset`` determines where diagonals are taken from input tensor x:

    - If offset = 0, it is the main diagonal.
    - If offset > 0, it is above the main diagonal.
    - If offset < 0, it is below the main diagonal.
    
    Args:
        x (Tensor): The input tensor x. Must be at least 2-dimensional. The input data type should be bool, int32, int64, float16, float32, float64.
        offset (int, optional): Which diagonals in input tensor x will be taken. Default: 0 (main diagonals).
        axis1 (int, optional): The first axis with respect to take diagonal. Default: 0.
        axis2 (int, optional): The second axis with respect to take diagonal. Default: 1.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: a partial view of input tensor in specify two dimensions, the output data type is the same as input data type.

    Examples:
        .. code-block:: python

            import paddle

            x = paddle.rand([2,2,3],'float32')
            print(x)
            # Tensor(shape=[2, 2, 3], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #        [[[0.45661032, 0.03751532, 0.90191704],
            #          [0.43760979, 0.86177313, 0.65221709]],

            #         [[0.17020577, 0.00259554, 0.28954273],
            #          [0.51795638, 0.27325270, 0.18117726]]])

            out1 = paddle.diagonal(x)
            print(out1)
            #Tensor(shape=[3, 2], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #       [[0.45661032, 0.51795638],
            #        [0.03751532, 0.27325270],
            #        [0.90191704, 0.18117726]])

            out2 = paddle.diagonal(x, offset=0, axis1=2, axis2=1)
            print(out2)
            #Tensor(shape=[2, 2], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #       [[0.45661032, 0.86177313],
            #        [0.17020577, 0.27325270]])

            out3 = paddle.diagonal(x, offset=1, axis1=0, axis2=1)
            print(out3)
            #Tensor(shape=[3, 1], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #       [[0.43760979],
            #        [0.86177313],
            #        [0.65221709]])

            out4 = paddle.diagonal(x, offset=0, axis1=1, axis2=2)
            print(out4)
            #Tensor(shape=[2, 2], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #       [[0.45661032, 0.86177313],
            #        [0.17020577, 0.27325270]])
            
    r#  r$  r%  c                 S   s   t | jdg dd t| j}t|dksJ dt| |dkr#|nt|| }|dkr/|nt|| }|t|k sKJ dt| t|d |f |t|k saJ d	t| t|d |f ||ksmJ d
||f d S )Nr   )r   r\   r]   rY   r?   r@   diagonalr   r  r   r  r   r  r   r!  r"  rR   rR   rS   r     s6   

zdiagonal.<locals>.__check_inputr(  r^   r   r&  rD   r   N)r(  )
r   r;   r(  r   r<   r   rI   rK   rP   rL   r'  rR   rR   rS   r(  v  s$   Ar(  kronc                 C   s   t  r	t| |S t rt| |S td
i t }t| dg dd t|dg dd |j| j	d}|j
d| |dd|id |S )aa  

    ${comment}

    Args:
        x (Tensor): the fist operand of kron op, data type: float16, float32, float64, int32 or int64.
        y (Tensor): the second operand of kron op, data type: float16, float32, float64, int32 or int64. Its data type should be the same with x.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: The output of kron, data type: float16, float32, float64, int32 or int64. Its data is the same with x.

    Examples:
        .. code-block:: python

            import paddle
            x = paddle.to_tensor([[1, 2], [3, 4]], dtype='int64')
            y = paddle.to_tensor([[1, 2, 3], [4, 5, 6], [7, 8, 9]], dtype='int64')
            out = paddle.kron(x, y)
            print(out)
            #        [[1, 2, 3, 2, 4, 6],
            #         [ 4,  5,  6,  8, 10, 12],
            #         [ 7,  8,  9, 14, 16, 18],
            #         [ 3,  6,  9,  4,  8, 12],
            #         [12, 15, 18, 16, 20, 24],
            #         [21, 24, 27, 28, 32, 36]])
    r)  r>   r   r   r^   r   rD   rE   N)r)  )r   r<   r)  r   r;   r   rI   r   rK   rP   rL   )r>   r   rN   rO   rQ   rR   rR   rS   r)    s   c           	      C   s   |du rd}nd}|dur| j t|krt| |} t r+|du r"d}t| ||ddS t rB|du r9t| d|S t| d|d|S t| dt	d t
  }t }| D ]\}}|dura|||< qUtd}|d	i |S )
a  
    The cumulative sum of the elements along a given axis. 
    
    Note:
        The first element of the result is the same as the first element of the input. 

    Args:
        x (Tensor): The input tensor needed to be cumsumed.
        axis (int, optional): The dimension to accumulate along. -1 means the last dimension. The default (None) is to compute the cumsum over the flattened array.
        dtype (str, optional): The data type of the output tensor, can be float32, float64, int32, int64. If specified, the input tensor is casted to dtype before the operation is performed. This is useful for preventing data type overflows. The default value is None. 
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor, the result of cumsum operator. 

    Examples:
        .. code-block:: python
            
            import paddle
            
            data = paddle.arange(12)
            data = paddle.reshape(data, (3, 4))

            y = paddle.cumsum(data)
            # [ 0  1  3  6 10 15 21 28 36 45 55 66]

            y = paddle.cumsum(data, axis=0)
            # [[ 0  1  2  3]
            #  [ 4  6  8 10]
            #  [12 15 18 21]]
            
            y = paddle.cumsum(data, axis=-1)
            # [[ 0  1  3  6]
            #  [ 4  9 15 22]
            #  [ 8 17 27 38]]

            y = paddle.cumsum(data, dtype='float64')
            print(y.dtype)
            # paddle.float64
    NTFr|   flattenr   r>   cumsumrR   )rP   r   r	   r   r;   r+  r   r<   r   r   rI   copydictr   r   )	r>   r   rP   rN   r*  Z
locals_varr   r   Z	_cum_sum_rR   rR   rS   r+    s*   )

r+  c                 C   s   |du rd}nd}|dur| j t|krt| |} t r+|du r"d}t| ||ddS t rB|du r9t| d|S t| d|d|S t| ddd	gd
 t	di t
 }|| j }|jd
d| id|i||dd |S )a  
    The logarithm of the cumulative summation of the exponentiation of the elements along a given axis. 

    For summation index j given by `axis` and other indices i, the result is

    .. math::

        logcumsumexp(x)_{ij} = log \sum_{i=0}^{j}exp(x_{ij})
    
    Note:
        The first element of the result is the same as the first element of the input.

    Args:
        x (Tensor): The input tensor.
        axis (int, optional): The dimension to do the operation along. -1 means the last dimension. The default (None) is to compute the cumsum over the flattened array.
        dtype (str, optional): The data type of the output tensor, can be float32, float64. If specified, the input tensor is casted to dtype before the operation is performed. This is useful for preventing data type overflows. The default value is None. 
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor, the result of logcumsumexp operator. 

    Examples:
        .. code-block:: python
            
            import paddle
            
            data = paddle.arange(12, dtype='float64')
            data = paddle.reshape(data, (3, 4))

            y = paddle.logcumsumexp(data)
            # [ 0.         1.3132617  2.4076061  3.4401898  4.4519143  5.4561934
            #   6.4577627  7.4583397  8.458551   9.45863   10.458658  11.458669 ]

            y = paddle.logcumsumexp(data, axis=0)
            # [[ 0.        1.        2.        3.      ]
            #  [ 4.01815   5.01815   6.01815   7.01815 ]
            #  [ 8.018479  9.018479 10.018479 11.018479]]
            
            y = paddle.logcumsumexp(data, axis=-1)
            # [[ 0.         1.3132617  2.4076061  3.4401898]
            #  [ 4.         5.3132615  6.407606   7.44019  ]
            #  [ 8.         9.313262  10.407606  11.440189 ]]

            y = paddle.logcumsumexp(data, dtype='float64')
            print(y.dtype)
            # paddle.float64
    NTFr|   r*  r   r>   r?   r@   logcumsumexprB   rD   )r   r*  r_   )r.  )rP   r   r	   r   r;   r.  r   r<   r   r   rI   rK   rL   )r>   r   rP   rN   r*  rO   rQ   rR   rR   rS   r.  R  s"   0
 r.  c                 C   s   |dur| j t|krt| |} t rt| |S t r#t| d|S t| dg dd t	|dt
d td	i t }|| j }|jdd| id|id|id |S )
a  
    Compute the cumulative product of the input tensor x along a given dimension dim.

    Note:
        The first element of the result is the same as the first element of the input.

    Args:
        x (Tensor): the input tensor need to be cumproded.
        dim (int): the dimension along which the input tensor will be accumulated. It need to be in the range of [-x.rank, x.rank), where x.rank means the dimensions of the input tensor x and -1 means the last dimension.
        dtype (str, optional): The data type of the output tensor, can be float32, float64, int32, int64, complex64, complex128. If specified, the input tensor is casted to dtype before the operation is performed. This is useful for preventing data type overflows. The default value is None.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor, the result of cumprod operator.

    Examples:
        .. code-block:: python

            import paddle

            data = paddle.arange(12)
            data = paddle.reshape(data, (3, 4))
            # [[ 0  1  2  3 ]
            #  [ 4  5  6  7 ]
            #  [ 8  9  10 11]]

            y = paddle.cumprod(data, dim=0)
            # [[ 0  1   2   3]
            #  [ 0  5  12  21]
            #  [ 0 45 120 231]]

            y = paddle.cumprod(data, dim=-1)
            # [[ 0   0   0    0]
            #  [ 4  20 120  840]
            #  [ 8  72 720 7920]]

            y = paddle.cumprod(data, dim=1, dtype='float64')
            # [[ 0.   0.   0.    0.]
            #  [ 4.  20. 120.  840.]
            #  [ 8.  72. 720. 7920.]]

            print(y.dtype)
            # paddle.float64

    Nr   r>   r   r   r?   r@   r\   r]   cumprodrB   rD   r_   )r0  )rP   r   r	   r   r;   r0  r   r<   r   r   r   r   rI   rK   rL   )r>   r   rP   rN   rO   rQ   rR   rR   rS   r0    s   /
r0  c                 C   sh   t  rt| S t rt| S td
i t }t| dg dd |	d}|j
dd| id|id |S )a  

    Return whether every element of input tensor is finite number or not.

    Args:
        x (Tensor): The input tensor, it's data type should be float16, float32, float64, int32, int64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        `Tensor`, the bool result which shows every element of `x` whether it is finite number or not.

    Examples:
        .. code-block:: python

            import paddle

            x = paddle.to_tensor([float('-inf'), -2, 3.6, float('inf'), 0, float('-nan'), float('nan')])
            out = paddle.isfinite(x)
            print(out)  # [False  True  True False  True False False]
    isfinite_v2r>   r   isfiniter   rB   rD   rE   N)r1  )r   r;   r2  r   r<   r1  r   rI   r   rK   rL   r>   rN   rO   rQ   rR   rR   rS   r2    s   


r2  c                 C   j   t  rt| S t rt| S tdi t }t| dg dd |j	dd}|j
dd| id|id	 |S )a  

    Return whether every element of input tensor is `+/-INF` or not.

    Args:
        x (Tensor): The input tensor, it's data type should be float16, float32, float64, int32, int64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        `Tensor`, the bool result which shows every element of `x` whether it is `+/-INF` or not.

    Examples:
        .. code-block:: python

            import paddle

            x = paddle.to_tensor([float('-inf'), -2, 3.6, float('inf'), 0, float('-nan'), float('nan')])
            out = paddle.isinf(x)
            print(out)  # [ True False False  True False False False]
    isinf_v2r>   r   isinfr   r^   rB   rD   rE   N)r5  )r   r;   r6  r   r<   r5  r   rI   r   rK   rL   r3  rR   rR   rS   r6    s   

r6  c                 C   r4  )a  

    Return whether every element of input tensor is `NaN` or not.

    Args:
        x (Tensor): The input tensor, it's data type should be float16, float32, float64, int32, int64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        `Tensor`, the bool result which shows every element of `x` whether it is `NaN` or not.

    Examples:
        .. code-block:: python

            import paddle
            
            x = paddle.to_tensor([float('-inf'), -2, 3.6, float('inf'), 0, float('-nan'), float('nan')])
            out = paddle.isnan(x)
            print(out)  # [False False False False False  True  True]
    isnan_v2r>   r   r   r   r^   rB   rD   rE   N)r7  )r   r;   r   r   r<   r7  r   rI   r   rK   rL   r3  rR   rR   rS   r     s   

r   c           	   	   C   s  |durt |dg dd | jt|krt| |} |}t|tr/|jd t| jkr,dnd}nI|durTt|tsTt|t	rBt|}nt|t
rK|g}n	tdt||du sgt|dksgt|t| jkridnd}|du sut|dkrxdg}t rt| |||S t rt| d	|d
|d|S tdi t }t| dg dd |j| d}t|tst|rt|}|jdd| id|i|||dd |S )a  
    Compute the product of tensor elements over the given axis.

    Args:
        x (Tensor): The input tensor, its data type should be float32, float64, int32, int64.
        axis (int|list|tuple, optional): The axis along which the product is computed. If :attr:`None`, 
            multiply all elements of `x` and return a Tensor with a single element, 
            otherwise must be in the range :math:`[-x.ndim, x.ndim)`. If :math:`axis[i]<0`, 
            the axis to reduce is :math:`x.ndim + axis[i]`. Default is None.
        keepdim (bool, optional): Whether to reserve the reduced dimension in the output Tensor. The result 
            tensor will have one fewer dimension than the input unless `keepdim` is true. Default is False.
        dtype (str|np.dtype, optional): The desired date type of returned tensor, can be float32, float64, 
            int32, int64. If specified, the input tensor is casted to dtype before operator performed. 
            This is very useful for avoiding data type overflows. The default value is None, the dtype 
            of output is the same as input Tensor `x`.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor, result of product on the specified dim of input tensor.
    
    Examples:
        .. code-block:: python

            import paddle

            # the axis is a int element
            x = paddle.to_tensor([[0.2, 0.3, 0.5, 0.9],
                                  [0.1, 0.2, 0.6, 0.7]])
            out1 = paddle.prod(x)
            # [0.0002268]

            out2 = paddle.prod(x, -1)
            # [0.027  0.0084]

            out3 = paddle.prod(x, 0)
            # [0.02 0.06 0.3  0.63]

            out4 = paddle.prod(x, 0, keepdim=True)
            # [[0.02 0.06 0.3  0.63]]

            out5 = paddle.prod(x, 0, dtype='int64')
            # [0 0 0 0]

            # the axis is list
            y = paddle.to_tensor([[[1.0, 2.0], [3.0, 4.0]],
                                  [[5.0, 6.0], [7.0, 8.0]]])
            out6 = paddle.prod(y, [0, 1])
            # [105. 384.]

            out7 = paddle.prod(y, (1, 2))
            # [  24. 1680.]

    NrP   rr   prodr   TFr   r   r   r   reduce_prodr   r^   rB   rD   r   r_   )r9  )r   rP   r   r	   rd   r   r   ru   rt   r   r   r   r   rF   r   r;   r9  r   r<   r   rI   r   rK   rJ   r   r   r   rL   )	r>   r   r   rP   rN   r   r   rO   rQ   rR   rR   rS   r8  8  sT   6





.
	r8  c                 C   sp   t  rt| S t rt| S t| dg dd td	i t }|j| j	d}|j
dd| gid|gid |S )
a  
    Returns sign of every element in `x`: 1 for positive, -1 for negative and 0 for zero.

    Args:
        x (Tensor): The input tensor. The data type can be float16, float32 or float64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: The output sign tensor with identical shape and data type to the input :attr:`x`.

    Examples:
        .. code-block:: python

          import paddle

          x = paddle.to_tensor([3.0, 0.0, -2.0, 1.7], dtype='float32')
          out = paddle.sign(x=x)
          print(out)  # [1.0, 0.0, -1.0, 1.0]
    r>   rn   signr^   rB   rD   rE   N)r:  )r   r;   r:  r   r<   r   r   rI   rK   rP   rL   r3  rR   rR   rS   r:    s   

r:  c                 C   sx   t  rt| S t rt| S t| dg dd t| dtd tdi t	 }|
| j}|jdd| id|id |S )	a  
    Tanh Activation Operator.

    .. math::
        out = \frac{e^{x} - e^{-x}}{e^{x} + e^{-x}}

    Args:
        x (Tensor): Input of Tanh operator, an N-D Tensor, with data type float32, float64 or float16.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Output of Tanh operator, a Tensor with same data type and shape as input.

    Examples:

        .. code-block:: python

            import paddle

            x = paddle.to_tensor([-0.4, -0.2, 0.1, 0.3])
            out = paddle.tanh(x)
            print(out)
            # [-0.37994896 -0.19737532  0.09966799  0.29131261]
    r>   rn   tanhrB   rD   rE   N)r;  )r   r;   r;  r   r<   r   r   r   r   rI   rK   rP   rL   r3  rR   rR   rS   r;    s   

r;  c                 C   s   t  rt| S t| S )z
    Inplace version of ``tanh`` API, the output Tensor will be inplaced with input ``x``.
    Please refer to :ref:`api_tensor_tanh`.
    )r   r;   tanh_r<   r>   rN   rR   rR   rS   r<    s   

r<  c                 C   sr   t  r	t| |S t rt| d|S t| dg dd td	i t }|j	dd| gid| gidt
|id | S )
ak  
    The API is usually used for control flow to increment the data of :attr:`x` by an amount :attr:`value`.
    Notice that the number of elements in :attr:`x` must be equal to 1.

    Args:
        x (Tensor): A tensor that must always contain only one element, its data type supports float32, float64, int32 and int64.
        value (float, optional): The amount to increment the data of :attr:`x`. Default: 1.0.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor, the elementwise-incremented tensor with the same shape and data type as :attr:`x`.

    Examples:
        .. code-block:: python

            import paddle

            data = paddle.zeros(shape=[1], dtype='float32')
            counter = paddle.increment(data)
            # [1.]

    stepr>   rr   	incrementrB   rD   r_   N)r?  )r   r;   Z
increment_r   r<   r?  r   r   rI   rL   rb   )r>   valuerN   rO   rR   rR   rS   r?    s   
r?  c              	   C   s.  |durt |ttfs|g}|sd}nt|t| jkrd}nd}t r4|r-tt| j}t| ||S t	 rO|dkrA|g krA|ndg}t
| d|d|d|S |dkr]|g kr]|dkr]|ndg||d	}t| d
dgd t|dttttdfd tdi t }|j| jd}|jdd| id|i|d |S )a  
    Computes the ``logical and`` of tensor elements over the given dimension.

    Args:
        x (Tensor): An N-D Tensor, the input data type should be `bool`.
        axis (int|list|tuple, optional): The dimensions along which the ``logical and`` is compute. If
            :attr:`None`, and all elements of :attr:`x` and return a
            Tensor with a single element, otherwise must be in the
            range :math:`[-rank(x), rank(x))`. If :math:`axis[i] < 0`,
            the dimension to reduce is :math:`rank + axis[i]`.
        keepdim (bool, optional): Whether to reserve the reduced dimension in the
            output Tensor. The result Tensor will have one fewer dimension
            than the :attr:`x` unless :attr:`keepdim` is true, default
            value is False.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: Results the ``logical and`` on the specified axis of input Tensor `x`,  it's data type is bool.

    Examples:
        .. code-block:: python

            import paddle

            # x is a bool Tensor with following elements:
            #    [[True, False]
            #     [True, True]]
            x = paddle.to_tensor([[1, 0], [1, 1]], dtype='int32')
            print(x)
            x = paddle.cast(x, 'bool')

            # out1 should be [False]
            out1 = paddle.all(x)  # [False]
            print(out1)

            # out2 should be [True, False]
            out2 = paddle.all(x, axis=0)  # [True, False]
            print(out2)

            # keepdim=False, out3 should be [False, True], out.shape should be (2,)
            out3 = paddle.all(x, axis=-1)  # [False, True]
            print(out3)

            # keepdim=True, out4 should be [[False], [True]], out.shape should be (2,1)
            out4 = paddle.all(x, axis=1, keepdim=True) # [[False], [True]]
            print(out4)
            
    NTFr   r   r   r   rR   r   r>   r   allr   r^   rB   rD   r_   )rA  )rd   rt   r   ru   r   r   r   r;   rA  r   r<   r   r   r   r   rF   r   rI   rK   rP   rL   r>   r   r   rN   r   r`   rO   rQ   rR   rR   rS   rA    s>   1 rA  c              	   C   s.  |durt |ttfs|g}|sd}nt|t| jkrd}nd}t r4|r-tt| j}t| ||S t	 rO|dkrA|g krA|ndg}t
| d|d|d|S |dkr]|g kr]|dkr]|ndg||d	}t| d
dgd t|dttttdfd tdi t }|j| jd}|jdd| id|i|d |S )a  
    Computes the ``logical or`` of tensor elements over the given dimension, and return the result.

    Args:
        x (Tensor): An N-D Tensor, the input data type should be `bool`.
        axis (int|list|tuple, optional): The dimensions along which the ``logical or`` is compute. If
            :attr:`None`, and all elements of :attr:`x` and return a
            Tensor with a single element, otherwise must be in the
            range :math:`[-rank(x), rank(x))`. If :math:`axis[i] < 0`,
            the dimension to reduce is :math:`rank + axis[i]`.
        keepdim (bool, optional): Whether to reserve the reduced dimension in the
            output Tensor. The result Tensor will have one fewer dimension
            than the :attr:`x` unless :attr:`keepdim` is true, default
            value is False.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: Results the ``logical or`` on the specified axis of input Tensor `x`,  it's data type is bool.

    Examples:
        .. code-block:: python

            import paddle

            x = paddle.to_tensor([[1, 0], [1, 1]], dtype='int32')
            x = paddle.assign(x)
            print(x)
            x = paddle.cast(x, 'bool')
            # x is a bool Tensor with following elements:
            #    [[True, False]
            #     [True, True]]

            # out1 should be [True]
            out1 = paddle.any(x)  # [True]
            print(out1)

            # out2 should be [True, True]
            out2 = paddle.any(x, axis=0)  # [True, True]
            print(out2)

            # keepdim=False, out3 should be [True, True], out.shape should be (2,)
            out3 = paddle.any(x, axis=-1)  # [True, True]
            print(out3)

            # keepdim=True, result should be [[True], [True]], out.shape should be (2,1)
            out4 = paddle.any(x, axis=1, keepdim=True)  # [[True], [True]]
            print(out4) 
            
    NTFr   r   r   r   rR   r   r>   r   anyr   r^   
reduce_anyrB   rD   r_   )rC  )rd   rt   r   ru   r   r   r   r;   rC  r   r<   rD  r   r   r   rF   r   rI   rK   rP   rL   rB  rR   rR   rS   rC  s  s>   2 rC  c                 C   s   t | |S )a  
    The function returns the shape of doing operation with broadcasting on tensors of x_shape and y_shape, please refer to :ref:`user_guide_broadcasting` for more details.

    Args:
        x_shape (list[int]|tuple[int]): A shape of tensor.
        y_shape (list[int]|tuple[int]): A shape of tensor.
        

    Returns:
        list[int], the result shape.

    Examples:
        .. code-block:: python

            import paddle

            shape = paddle.broadcast_shape([2, 1, 3], [1, 3, 1])
            # [2, 3, 3]
            
            # shape = paddle.broadcast_shape([2, 1, 3], [3, 3, 1])
            # ValueError (terminated with error message).

    )r   r   )r   r   rR   rR   rS   r     s   r   c                 C   sr   t  rt| S t rt| S t| dg dd td	i t }|j	|
 d}|jdd| id|gid |S )
a  
    This function computes the conjugate of the Tensor elementwisely.

    Args:
        x (Tensor): The input Tensor which hold the complex numbers. 
            Optional data types are: complex64, complex128, float32, float64, int32 or int64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        out (Tensor): The conjugate of input. The shape and data type is the same with input. If the elements of tensor is real type such as float32, float64, int32 or int64, the out is the same with input.

    Examples:
        .. code-block:: python

          import paddle
          
          data=paddle.to_tensor([[1+1j, 2+2j, 3+3j], [4+4j, 5+5j, 6+6j]])
          #Tensor(shape=[2, 3], dtype=complex64, place=CUDAPlace(0), stop_gradient=True,
          #       [[(1+1j), (2+2j), (3+3j)],
          #        [(4+4j), (5+5j), (6+6j)]])

          conj_data=paddle.conj(data)
          #Tensor(shape=[2, 3], dtype=complex64, place=CUDAPlace(0), stop_gradient=True,
          #       [[(1-1j), (2-2j), (3-3j)],
          #        [(4-4j), (5-5j), (6-6j)]])

    r>   r/  conjr^   rB   rD   rE   N)rE  )r   r;   rE  r   r   r<   r   r   rI   rK   rJ   rL   r3  rR   rR   rS   rE    s   

rE  c                 C   j   t  rt| S t rt| S t| dddgd td	i t }|| j	}|j
dd| id|id |S )
a  
    Calculates the digamma of the given input tensor, element-wise.

    .. math::
        Out = \Psi(x) = \frac{ \Gamma^{'}(x) }{ \Gamma(x) }

    Args:
        x (Tensor): Input Tensor. Must be one of the following types: float32, float64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.
    Returns:
        Tensor, the digamma of the input Tensor, the shape and data type is the same with input.

    Examples:
        .. code-block:: python

            import paddle

            data = paddle.to_tensor([[1, 1.5], [0, -2.2]], dtype='float32')
            res = paddle.digamma(data)
            print(res)
            # Tensor(shape=[2, 2], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #       [[-0.57721591,  0.03648996],
            #        [ nan       ,  5.32286835]])
    r>   r?   r@   digammarB   rD   rE   N)rG  )r   r;   rG  r   r<   r   r   rI   rK   rP   rL   r3  rR   rR   rS   rG    s   

rG  c                 C   rF  )
a  
    Calculates the lgamma of the given input tensor, element-wise.

    This operator performs elementwise lgamma for input $X$.
    :math:`out = log\Gamma(x)`


    Args:
        x (Tensor): Input Tensor. Must be one of the following types: float32, float64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor, the lgamma of the input Tensor, the shape and data type is the same with input.

    Examples:
        .. code-block:: python

            import paddle

            x = paddle.to_tensor([-0.4, -0.2, 0.1, 0.3])
            out = paddle.lgamma(x)
            print(out)
            # [1.31452441, 1.76149750, 2.25271273, 1.09579802]
    r>   r?   r@   lgammarB   rD   rE   N)rH  )r   r;   rH  r   r<   r   r   rI   rK   rP   rL   r3  rR   rR   rS   rH  :  s   

rH  c                 C   s   t | dddd|dS )a  
    This function computes the negative of the Tensor elementwisely.

    Args:
        x (Tensor): Input of neg operator, an N-D Tensor, with data type float32, float64, int8, int16, int32, or int64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        out (Tensor): The negative of input Tensor. The shape and data type are the same with input Tensor.

    Examples:
        .. code-block:: python

            import paddle

            x = paddle.to_tensor([-0.4, -0.2, 0.1, 0.3])
            out = paddle.neg(x)
            print(out)
            # [0.4 0.2 -0.1 -0.3]
    g      rU   TN)rV   rW   rX   rh   rN   ra   r=  rR   rR   rS   neg_  s   rI  c                 C   s   t  r	t| |S t rt| |S t| dg dd t|dg dd td
i t }| |d}|j| j	d}|j
d|d|id |S )aW  
    Element-wise arctangent of x/y with consideration of the quadrant.

    Equation:
        .. math::

            atan2(x,y)=\left\{\begin{matrix}
            & tan^{-1}(\frac{x}{y}) & y > 0 \\
            & tan^{-1}(\frac{x}{y}) + \pi & x>=0, y < 0 \\
            & tan^{-1}(\frac{x}{y}) - \pi & x<0, y < 0 \\
            & +\frac{\pi}{2} & x>0, y = 0 \\
            & -\frac{\pi}{2} & x<0, y = 0 \\
            &\text{undefined} & x=0, y = 0
            \end{matrix}\right.

    Args:
        x (Tensor): An N-D Tensor, the data type is int32, int64, float16, float32, float64.
        y (Tensor): An N-D Tensor, must have the same type as `x`.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        out (Tensor): An N-D Tensor, the shape and data type is the same with input (The output data type is float64 when the input data type is int).

    Examples:
        .. code-block:: python

            import paddle

            x = paddle.to_tensor([-1, +1, +1, -1]).astype('float32')
            #Tensor(shape=[4], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #       [-1,  1,  1, -1])

            y = paddle.to_tensor([-1, -1, +1, +1]).astype('float32')
            #Tensor(shape=[4], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #       [-1,  -1,  1, 1])

            out = paddle.atan2(x, y)
            #Tensor(shape=[4], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #       [-2.35619450,  2.35619450,  0.78539819, -0.78539819])

    r>   r  atan2r   )ZX1ZX2r^   rD   rE   N)rJ  )r   r;   rJ  r   r<   r   r   rI   rK   rP   rL   )r>   r   rN   rO   rG   rQ   rR   rR   rS   rJ  w  s   +

rJ  c                 C   s   |dkrd}t  rt| d|S t rt| |S t| dg dd td
i t }|| j	}|j
dd| id|id|id	 |S )a  
    This function generates a new tensor with the logit of the elements of input x. x is clamped to [eps, 1-eps] when eps is not zero. When eps is zero and x < 0 or x > 1, the function will yields NaN.

    .. math::
 
        logit(x) = ln(\frac{x}{1 - x})

    where

    .. math::

        x_i=
            \left\{\begin{array}{rcl}
                x_i & &\text{if } eps == Default \\
                eps & &\text{if } x_i < eps \\
                x_i & &\text{if } eps <= x_i <= 1-eps \\
                1-eps & &\text{if } x_i > 1-eps
            \end{array}\right.

    Args:
        x (Tensor): The input Tensor with data type float32, float64.
        eps (float, optional):  the epsilon for input clamp bound. Default is None.
        name (str, optional): Name for the operation (optional, default is None).
            For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        out(Tensor): A Tensor with the same data type and shape as ``x`` .

    Examples:
        .. code-block:: python

            import paddle

            x = paddle.to_tensor([0.2635, 0.0106, 0.2780, 0.2097, 0.8095])
            out1 = paddle.logit(x)
            print(out1)
            # [-1.0277, -4.5365, -0.9544, -1.3269,  1.4468]  

    NrU   epsr>   rn   logitrB   rD   r_   )rL  )r   r<   rL  r   r;   r   r   rI   rK   rP   rL   )r>   rK  rN   rO   rQ   rR   rR   rS   rL    s    )rL  c                 C   s  t  r"t|dttjtfd t|trtj|| jd}t	
| ||S t r9t|tr2tj|| jd}t
| ||S t|trHtjdg|| jd}t| dddgd t|d	ddgd t|dddgd tdi t }| ||d
}|j| jd}|jd|d|id |S )a  
    Does a linear interpolation between x and y based on weight.

    Equation:
        .. math::

            lerp(x, y, weight) = x + weight * (y - x).

    Args:
        x (Tensor): An N-D Tensor with starting points, the data type is float32, float64.
        y (Tensor): An N-D Tensor with ending points, the data type is float32, float64.
        weight (float|Tensor): The weight for the interpolation formula. When weight is Tensor, the data type is float32, float64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        out (Tensor): An N-D Tensor, the shape and data type is the same with input.

    Example:
        .. code-block:: python

            import paddle
            
            x = paddle.arange(1., 5., dtype='float32')
            y = paddle.empty([4], dtype='float32')
            y.fill_(10.)
            out = paddle.lerp(x, y, 0.5)
            # out: [5.5, 6., 6.5, 7.]

    weightlerpr^   r   )r   Z
fill_valuerP   r>   r?   r@   r   )rB   r   ZWeightrD   rE   N)rN  )r   r   rb   r   r   r   rd   	to_tensorrP   r;   rN  r   r<   fullr   r   rI   rK   rL   )r>   r   rM  rN   rO   rG   rQ   rR   rR   rS   rN    s&   


rN  c                 C   s   t | j|j}t|dttjtfd t|tr!tj|g| j	d}nt|tjtfr/t ||j}|| jkr=t
d|| jt rGt| ||S t| ||S )z
    Inplace version of ``lerp`` API, the output Tensor will be inplaced with input ``x``.
    Please refer to :ref:`api_tensor_lerp`.
    rM  rN  r^   r   )r   r   r   rb   r   r   r   rd   rO  rP   rv   r   r   r;   lerp_r<   )r>   r   rM  rN   r   rR   rR   rS   rQ  !  s   

rQ  c                 C   sn   t  rt| S t| dddgd t rt| S td
i t }|j	| j
d}|jdd| id|id |S )a  
    The inverse error function of x. Please refer to :ref:`api_paddle_erf`

        .. math::

            erfinv(erf(x)) = x.

    Args:
        x (Tensor): An N-D Tensor, the data type is float32, float64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        out (Tensor), an N-D Tensor, the shape and data type is the same with input.

    Example:
        .. code-block:: python

            import paddle
            
            x = paddle.to_tensor([0, 0.5, -1.], dtype="float32")
            out = paddle.erfinv(x)
            # out: [0, 0.4769, -inf]

    r>   r?   r@   erfinvr^   rB   rD   rE   N)rR  )r   r;   rR  r   r   r   r<   r   rI   rK   rP   rL   r3  rR   rR   rS   rR  3  s   

rR  c                 C   s.   t | dtjtfd t rt| S t| S )z
    Inplace version of ``erfinv`` API, the output Tensor will be inplaced with input ``x``.
    Please refer to :ref:`api_tensor_erfinv`.
    r>   rR  )r   r   r   r   r   r;   erfinv_r<   r=  rR   rR   rS   rS  Y  s   

rS  c                 C   s   dt j }t rt| jdv rt| dd} t| |ddS t	 r5t| jdv r.t| dd} t
| d|S t| dg d	d
 tdi t }| }t| jdv rh|jtjd}|jdd| id|i| jtjdd |j|jd}|jdd|id|id|id |S )a  
    Convert each of the elements of input x from angles in radians to degrees.
    
    Equation:
        .. math::

            rad2deg(x)=180/ \pi * x

    Args:
        x (Tensor): An N-D Tensor, the data type is float32, float64, int32, int64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        out (Tensor): An N-D Tensor, the shape and data type is the same with input (The output data type is float32 when the input data type is int).

    Examples:
        .. code-block:: python

            import paddle
            import math

            x1 = paddle.to_tensor([3.142, -3.142, 6.283, -6.283, 1.570, -1.570])
            result1 = paddle.rad2deg(x1)
            print(result1)
            # Tensor(shape=[6], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #         [180.02334595, -180.02334595,  359.98937988, -359.98937988,
            #           9.95437622 , -89.95437622])

            x2 = paddle.to_tensor(math.pi/2)
            result2 = paddle.rad2deg(x2)
            print(result2)
            # Tensor(shape=[1], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #         [90.])
                     
            x3 = paddle.to_tensor(1)
            result3 = paddle.rad2deg(x3)
            print(result3)
            # Tensor(shape=[1], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #         [57.29578018])
       r\   r]   r?   r^   rU   TrV   r>   r   rad2degr	   rB   rD   r   r_   N)rV  r  pir   r   rP   r	   r;   rV   r   r   r<   r   r   rI   rK   r?   rL   )r>   rN   Zrad2deg_scalerO   out_castrQ   rR   rR   rS   rV  d  s,   
)rV  c                 C   s   t jd }t rt| jdv rt| dd} t| |ddS t	 r5t| jdv r.t| dd} t
| d|S t| dg d	d
 tdi t }| }t| jdv rh|jtjd}|jdd| id|i| jtjdd |j|jd}|jdd|id|id|id |S )a  
    Convert each of the elements of input x from degrees to angles in radians.
        .. math::

            deg2rad(x)=\pi * x / 180

    Args:
        x (Tensor): An N-D Tensor, the data type is float32, float64, int32, int64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        out (Tensor): An N-D Tensor, the shape and data type is the same with input (The output data type is float32 when the input data type is int).

    Examples:
        .. code-block:: python

            import paddle
            x1 = paddle.to_tensor([180.0, -180.0, 360.0, -360.0, 90.0, -90.0])
            result1 = paddle.deg2rad(x1)
            print(result1)
            # Tensor(shape=[6], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #         [3.14159274, -3.14159274,  6.28318548, -6.28318548,  1.57079637,
            #           -1.57079637])

            x2 = paddle.to_tensor(180)
            result2 = paddle.deg2rad(x2)
            print(result2)
            # Tensor(shape=[1], dtype=float32, place=CUDAPlace(0), stop_gradient=True,
            #         [3.14159274])
    g     f@rU  r?   r^   rU   TrV   r>   r   deg2radr	   rB   rD   r   r_   N)rZ  rW  )r>   rN   Zdeg2rad_scalerO   rY  rQ   rR   rR   rS   rZ    s,   
rZ  c                 C   s   t | j|j}t | |} t ||}t | } t |}dd }dd }t  r=|| |r;|| |\} }|| |s/| S t| dddgd t|d	ddgd t jj	||| |g\}}|S )
u  
    Computes the element-wise greatest common divisor (GCD) of input |x| and |y|.
    Both x and y must have integer types.
    
    Note:
        gcd(0,0)=0, gcd(0, y)=|y|

        If x.shape != y.shape, they must be broadcastable to a common shape (which becomes the shape of the output).

    Args:
        x (Tensor): An N-D Tensor, the data type is int32，int64. 
        y (Tensor): An N-D Tensor, the data type is int32，int64. 
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        out (Tensor): An N-D Tensor, the data type is the same with input.

    Examples:
        .. code-block:: python

            import paddle
            
            x1 = paddle.to_tensor(12)
            x2 = paddle.to_tensor(20)
            paddle.gcd(x1, x2)
            # Tensor(shape=[1], dtype=int64, place=CUDAPlace(0), stop_gradient=True,
            #        [4])

            x3 = paddle.arange(6)
            paddle.gcd(x3, x2)
            # Tensor(shape=[6], dtype=int64, place=CUDAPlace(0), stop_gradient=True,
            #        [20, 1 , 2 , 1 , 4 , 5])

            x4 = paddle.to_tensor(0)
            paddle.gcd(x4, x2)
            # Tensor(shape=[1], dtype=int64, place=CUDAPlace(0), stop_gradient=True,
            #        [20])

            paddle.gcd(x4, x4)
            # Tensor(shape=[1], dtype=int64, place=CUDAPlace(0), stop_gradient=True,
            #        [0])
            
            x5 = paddle.to_tensor(-20)
            paddle.gcd(x1, x5)
            # Tensor(shape=[1], dtype=int64, place=CUDAPlace(0), stop_gradient=True,
            #        [4])
    c                 S   s   t |dkS Nr   )r   rC  r   rR   rR   rS   _gcd_cond_fn  s   zgcd.<locals>._gcd_cond_fnc              	   S   sx   |dk}t ||t |j|j}t ||| t |t | |t |j|j} }t | |k || t | |k | |fS r[  )r   r   onesr   rP   modzeros)r>   r   Zy_not_equal_0Zy_saferR   rR   rS   _gcd_body_fn  s    $zgcd.<locals>._gcd_body_fnr>   r\   r]   gcdr   )
r   r   r   Zbroadcast_tor   r   r   staticnnZ
while_loop)r>   r   rN   r   r\  r`  rQ   r   rR   rR   rS   ra    s    0




ra  c                 C   s^   t | |}t |d}t |t |j|j|}t |t |j|jt | | | }|S )u  
    Computes the element-wise least common multiple (LCM) of input |x| and |y|.
    Both x and y must have integer types.
    
    Note:
        lcm(0,0)=0, lcm(0, y)=0

        If x.shape != y.shape, they must be broadcastable to a common shape (which becomes the shape of the output).

    Args:
        x (Tensor): An N-D Tensor, the data type is int32，int64. 
        y (Tensor): An N-D Tensor, the data type is int32，int64. 
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        out (Tensor): An N-D Tensor, the data type is the same with input.

    Examples:
        .. code-block:: python

            import paddle
            
            x1 = paddle.to_tensor(12)
            x2 = paddle.to_tensor(20)
            paddle.lcm(x1, x2)
            # Tensor(shape=[1], dtype=int64, place=CUDAPlace(0), stop_gradient=True,
            #        [60])

            x3 = paddle.arange(6)
            paddle.lcm(x3, x2)
            # Tensor(shape=[6], dtype=int64, place=CUDAPlace(0), stop_gradient=True,
            #        [0, 20, 20, 60, 20, 20])

            x4 = paddle.to_tensor(0)
            paddle.lcm(x4, x2)
            # Tensor(shape=[1], dtype=int64, place=CUDAPlace(0), stop_gradient=True,
            #        [0])

            paddle.lcm(x4, x4)
            # Tensor(shape=[1], dtype=int64, place=CUDAPlace(0), stop_gradient=True,
            #        [0])
            
            x5 = paddle.to_tensor(-20)
            paddle.lcm(x1, x5)
            # Tensor(shape=[1], dtype=int64, place=CUDAPlace(0), stop_gradient=True,
            #        [60])
    r   )	r   ra  equalr   r]  r   rP   r_  r   )r>   r   rN   dZ	d_equal_0Zd_saferQ   rR   rR   rS   lcm&  s
   0(rf  c              
   C   s`  |dk r|t | j }|t | jkrt | j}|dk rd}| j}|g}tdd tt |D }t rd}	g }
|durG|durG|| |g}
d}	n|durR|| g}
d}	n
|dur\| |g}
d}	|	ret|
|}n| }d}d}|j| }dg}|d|f7 }|d	 g}|d
|f7 }t|||||g }d	g}|d|f7 }|g}|d
|f7 }t|||||g }| jt	j
krt||S t||S t r^d}	g }
|dur|dur|| |g}
d}	n|dur|| g}
d}	n
|dur| |g}
d}	|	rt }t|
|d| n| }d}d}|j| }dg}|d|f7 }|d	 g}|d
|f7 }tj|ddddd|d|g	|R  }d	g}|d|f7 }|g}|d
|f7 }tj|ddddd|d|g	|R  }| jt	j
krWt||S t|||dS t| dg dd t|dtd tdi t }d}	g }
|dur|dur|| |g}
d}	n|dur|| g}
d}	n|dur| |g}
d}	|	r||}|jdd|
id|gid|id n| }|j| }d|i}dg}|d	 g}||d< ||d
< ||}|jdd|i|d|id d|i}d	g}|g}||d< ||d
< ||}|jdd|i|d|id |t	j
kr'||}|jd||dd|id |S t|||d}|S )a  
    Computes the n-th forward difference along the given axis.
    The first-order differences is computed by using the following formula: 

    .. math::

        out[i] = x[i+1] - x[i]
    
    Higher-order differences are computed by using paddle.diff() recursively. 
    Only n=1 is currently supported.

    Args:
        x (Tensor): The input tensor to compute the forward difference on
        n (int, optional): The number of times to recursively compute the difference. 
                          Only support n=1. Default:1
        axis (int, optional): The axis to compute the difference along. Default:-1
        prepend (Tensor, optional): The tensor to prepend to input along axis before computing the difference.
                                   It's dimensions must be equivalent to that of x, 
                                   and its shapes must match x's shape except on axis.
        append (Tensor, optional): The tensor to append to input along axis before computing the difference, 
                                   It's dimensions must be equivalent to that of x, 
                                   and its shapes must match x's shape except on axis.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.
    
    Returns:
        Tensor: The output tensor with same dtype with x.

    Examples:
        .. code-block:: python

            import paddle

            x = paddle.to_tensor([1, 4, 5, 2])
            out = paddle.diff(x)
            print(out)
            # out:
            # [3, 1, -3]

            y = paddle.to_tensor([7, 9])
            out = paddle.diff(x, append=y)
            print(out)
            # out: 
            # [3, 1, -3, 5, 2]

            z = paddle.to_tensor([[1, 2, 3], [4, 5, 6]])
            out = paddle.diff(z, axis=0)
            print(out)
            # out:
            # [[3, 3, 3]]
            out = paddle.diff(z, axis=1)
            print(out)
            # out:
            # [[1, 1], [1, 1]]
    r   c                 s   s    | ]}d V  qdS )r   NrR   ).0r   rR   rR   rS   	<genexpr>  s    zdiff.<locals>.<genexpr>FNTrR   Zstartsr   Zendsr   axesinfer_flagsr  r>   )r?   r@   r   r\   r]   diffconcatrB   rD   r_   slicer   r   logical_xorr   rE   )rk  )ru   r   rP   rt   r   r   r;   rl  rm  r   r   rn  r   r   r   r<   r:   r   r   r   r   rI   rK   rL   )r>   nr   prependappendrN   rP   ri  rj  Zhas_pendZ
input_listZ	new_inputZattrs_1Zattrs_2Zdim_lenZstarts_1Zends_1Zinput_frontZstarts_2Zends_2Z
input_backrO   rQ   rR   rR   rS   rk  _  s  8















rk  c                 C   s   t  rt| S t rt| S t| dg dd d}t|fi t }d| i}|j	t
| jd}d|i}|j|||d |S )ax  
    Element-wise angle of complex numbers. For non-negative real numbers, the angle is 0 while 
    for negative real numbers, the angle is :math:`\pi`.

    Equation:
        .. math::

            angle(x)=arctan2(x.imag, x.real)

    Args:
        x (Tensor): An N-D Tensor, the data type is complex64, complex128, or float32, float64 .
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: An N-D Tensor of real data type with the same precision as that of x's data type.

    Examples:
        .. code-block:: python

            import paddle

            x = paddle.to_tensor([-2, -1, 0, 1]).unsqueeze(-1).astype('float32')
            y = paddle.to_tensor([-2, -1, 0, 1]).astype('float32')
            z = x + 1j * y
            print(z)
            # Tensor(shape=[4, 4], dtype=complex64, place=Place(cpu), stop_gradient=True,
            #        [[(-2-2j), (-2-1j), (-2+0j), (-2+1j)],
            #         [(-1-2j), (-1-1j), (-1+0j), (-1+1j)],
            #         [-2j    , -1j    ,  0j    ,  1j    ],
            #         [ (1-2j),  (1-1j),  (1+0j),  (1+1j)]])

            theta = paddle.angle(z)
            print(theta)
            # Tensor(shape=[4, 4], dtype=float32, place=Place(cpu), stop_gradient=True,
            #        [[-2.35619450, -2.67794514,  3.14159274,  2.67794514],
            #         [-2.03444386, -2.35619450,  3.14159274,  2.35619450],
            #         [-1.57079637, -1.57079637,  0.        ,  1.57079637],
            #         [-1.10714877, -0.78539819,  0.        ,  0.78539819]])
    r>   )r?   r@   r   r   anglerB   r^   rD   rE   )r   r;   rr  r   r   r<   r   r   rI   rK   r
   rP   rL   )r>   rN   r   rO   rG   rQ   rH   rR   rR   rS   rr  %  s    )

rr  c                 C   s:   d}d}d}t  rt| ||||dS tt|fi t S )a  
    Computes the Heaviside step function determined by corresponding element in y for each element in x. The equation is

    .. math::
        heaviside(x, y)=
            \left\{
                \begin{array}{lcl}
                0,& &\text{if} \ x < 0, \\
                y,& &\text{if} \ x = 0, \\
                1,& &\text{if} \ x > 0.
                \end{array}
            \right.

    Note:
        ``paddle.heaviside`` supports broadcasting. If you want know more about broadcasting, please refer to :ref:`user_guide_broadcasting`.

    Args:
        x (Tensor): The input tensor of Heaviside step function, it's data type should be float16, float32, float64, int32 or int64.
        y (Tensor): The tensor that determines a Heaviside step function, it's data type should be float16, float32, float64, int32 or int64.
        name (str, optional): Name for the operation (optional, default is None). Normally there is no need for user to set this property. For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        N-D Tensor. A location into which the result is stored. If x and y have different shapes and are broadcastable, the resulting tensor shape is the shape of x and y after broadcasting. If x, y have the same shape, its shape is the same as x and y.

    Examples:
        .. code-block:: python

            import paddle
            x = paddle.to_tensor([-0.5, 0, 0.5])
            y = paddle.to_tensor([0.1])
            paddle.heaviside(x, y)
            #    [0.        , 0.10000000, 1.        ]
            x = paddle.to_tensor([[-0.5, 0, 0.5], [-0.5, 0.5, 0]])
            y = paddle.to_tensor([0.1, 0.2, 0.3])
            paddle.heaviside(x, y)
            #    [[0.        , 0.20000000, 1.        ],
            #     [0.        , 1.        , 0.30000001]]
    Zelementwise_heavisider|   Nr~   )r   r   r   r   rI   r   rR   rR   rS   	heaviside^  s   '
rs  c           	      C   s   d}d}d}| j tjtjtjtjfvrtd| j t r)t	
| }t	| |S t r:t
| }t| ||||dS d| i}i }tdi t }t| dg dd |j| j d	}|jd||d
|id tt|fi t S )aS  
    This API is used to return the fractional portion of each element in input.

    Args:
        x (Tensor): The input tensor, which data type should be int32, int64, float32, float64.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: The output Tensor of frac.

    Examples:
        .. code-block:: python

            import paddle

            input = paddle.to_tensor([[12.22000003, -1.02999997],
                                    [-0.54999995, 0.66000003]])
            output = paddle.frac(input)
            print(output)
            # Tensor(shape=[2, 2], dtype=float32, place=Place(cpu), stop_gradient=True,
            #        [[ 0.22000003, -0.02999997],
            #         [-0.54999995,  0.66000003]])
    r:   r|   NzZThe data type of input must be one of ['int32', 'int64', 'float32', 'float64'], but got {}r~   rB   r   r   r^   rD   r   r   )rP   r   r\   r]   r?   r@   r   r   r   r;   r   r   r   r<   r   r   rI   r   rK   rL   r   )	r>   rN   r   r   rh   r   rG   r`   rO   rR   rR   rS   frac  s0   



rt  c                 C   s   | j tjtjtjtjtjfvrtd| j t	| rEt
| }t| }tj|dd}|| }t|}tt|||}t|S t| S )a,  
    For complex tensor, this API returns a new tensor whose elements have the same angles as the corresponding
    elements of input and absolute values of one.
    For other float dtype tensor,
    this API returns sign of every element in `x`: 1 for positive, -1 for negative and 0 for zero, same as paddle.sign.

    Args:
        x (Tensor): The input tensor, which data type should be float16, float32, float64, complex64, complex128.
        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor: A sign Tensor for real input, or normalized Tensor for complex input, shape and data type are same as input.

    Examples:
        .. code-block:: Python

            import paddle

            x = paddle.to_tensor([[3 + 4j, 7 - 24j, 0, 1 + 2j], [6 + 8j, 3, 0, -2]])
            print(paddle.sgn(x))
            #[[0.6+0.8j       0.28-0.96j      0.+0.j      0.4472136+0.8944272j]
            # [0.6+0.8j       1.+0.j          0.+0.j      -1.+0.j]]

    znThe data type of input must be one of ['float16', 'float32', 'float64', 'complex64', 'complex128'], but got {}r|   r  )rP   r   rY   r?   r@   r   r   r   r   Z
is_complexZas_realr   Z	unsqueezer   r   r   Z
as_complexr:  )r>   rN   Zexpand_xZx_absr  r_  rR   rR   rS   sgn  s   





ru  raisec                 C   s  |dvrt d|t r2t|tjtfs tdt||j	tj
tjfvr1td|j	n	t|dddgd |  }| }|jd	 }|d
krXt|dk || |}n'|dkrst|dk || |}t||k|| |}n|dkrt|d|d }|||j}|S )a  
    Returns a new tensor with the elements of input tensor x at the given index.
    The input tensor is treated as if it were viewed as a 1-D tensor.
    The result takes the same shape as the index.

    Args:
        x (Tensor): An N-D Tensor, its data type should be int32, int64, float32, float64.
        index (Tensor): An N-D Tensor, its data type should be int32, int64.
        mode (str, optional): Specifies how out-of-bounds index will behave. the candicates are ``'raise'``, ``'wrap'`` and ``'clip'``.

            - ``'raise'``: raise an error (default);
            - ``'wrap'``: wrap around;
            - ``'clip'``: clip to the range. ``'clip'`` mode means that all indices that are too large are replaced by the index that addresses the last element. Note that this disables indexing with negative numbers.

        name (str, optional): Name for the operation (optional, default is None). For more information, please refer to :ref:`api_guide_Name`.

    Returns:
        Tensor, Tensor with the same shape as index, the data type is the same with input.

    Examples:
        .. code-block:: python

            import paddle

            x_int = paddle.arange(0, 12).reshape([3, 4])
            x_float = x_int.astype(paddle.float64)

            idx_pos = paddle.arange(4, 10).reshape([2, 3])  # positive index
            idx_neg = paddle.arange(-2, 4).reshape([2, 3])  # negative index
            idx_err = paddle.arange(-2, 13).reshape([3, 5])  # index out of range

            paddle.take(x_int, idx_pos)
            # Tensor(shape=[2, 3], dtype=int64, place=Place(cpu), stop_gradient=True,
            #        [[4, 5, 6],
            #         [7, 8, 9]])

            paddle.take(x_int, idx_neg)
            # Tensor(shape=[2, 3], dtype=int64, place=Place(cpu), stop_gradient=True,
            #        [[10, 11, 0 ],
            #         [1 , 2 , 3 ]])

            paddle.take(x_float, idx_pos)
            # Tensor(shape=[2, 3], dtype=float64, place=Place(cpu), stop_gradient=True,
            #        [[4., 5., 6.],
            #         [7., 8., 9.]])

            x_int.take(idx_pos)
            # Tensor(shape=[2, 3], dtype=int64, place=Place(cpu), stop_gradient=True,
            #        [[4, 5, 6],
            #         [7, 8, 9]])

            paddle.take(x_int, idx_err, mode='wrap')
            # Tensor(shape=[3, 5], dtype=int32, place=Place(cpu), stop_gradient=True,
            #        [[10, 11, 0 , 1 , 2 ],
            #         [3 , 4 , 5 , 6 , 7 ],
            #         [8 , 9 , 10, 11, 0 ]])

            paddle.take(x_int, idx_err, mode='clip')
            # Tensor(shape=[3, 5], dtype=int32, place=Place(cpu), stop_gradient=True,
            #        [[0 , 0 , 0 , 1 , 2 ],
            #         [3 , 4 , 5 , 6 , 7 ],
            #         [8 , 9 , 10, 11, 11]])

    )rv  wrapr  zD'mode' in 'take' should be 'raise', 'wrap', 'clip', but received {}.z.The type of 'index' must be Tensor, but got {}zFThe data type of 'index' must be one of ['int32', 'int64'], but got {}rs   r\   r]   taker|   rv  r   rw  r  r   )rv   r   r   r   rd   r   r   r   rF   rP   r\   r]   r   r*  r   r   r  Zindex_selectr   )r>   rs   moderN   Zinput_1dZindex_1dZ	max_indexrQ   rR   rR   rS   rx    sB   A


rx  )N)rT   rU   TNN)rj   rk   N)r|   NFN)NNFN)NFN)rT   rT   N)NNN)r   r   r   N)NFNN)rT   N)NN)r   r|   NNN)rv  N)__doc__
__future__r   re   r  Zpaddle.common_ops_importr   r   r   r   r   Zmanipulationr	   Zcreationr
   Zlayer_function_generatorr   r   r   r   rb  r   Z	frameworkr   r   r   r   r   Zfluid.frameworkr   r   Zfluid.data_feederr   r   r   r   Zfluid.dygraph.inplace_utilsr   Zfluid.layersr   opsr   r   r   r    r!   r"   r#   r$   r%   r&   r'   r(   r)   r*   r+   r,   r-   r.   r/   r0   r1   r2   r3   r4   r5   r6   r7   r8   r9   r:   r;   r<   __all__ZVarTypeZUINT8ZINT8ZINT16ZINT32ZINT64Z_supported_int_dtype_ZFP32ZFP64Z_supported_float_dtype_rA   rV   ro   rp   rz   r   r   r   r   r   r   r   r   r   r   r   r   r^  Z	floor_modr   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r  r  r  r  r	  r  r  r  r  r  r  r  r  r(  r)  r+  r.  r0  r2  r6  r   r8  r:  r;  r<  r?  rA  rC  r   rE  rG  rH  rI  rJ  rL  rN  rQ  rR  rS  rV  rZ  ra  rf  rk  rr  rs  rt  ru  rx  rR   rR   rR   rS   <module>   sX  	

)
N
+K
P
%@
C

+
)+

5
@
@
B
C 

8
CA
\
/
sS
=
G
5
E/

h
h
q
q
%
4
4f

Wo
)
C
H
?


!
e
#&


(
Z[

+
&
%

;
96
&


?
5
N
9 
G
9
/
1)