o
    d                     @  s  d dl mZ d dlZd dlZd dlZd dlmZmZmZ d dl	Z	d dl
Zd dlmZ d dlmZmZmZmZ d dlmZmZmZmZmZmZmZmZmZ d dlmZ d dlm Z  d d	l!m"Z"m#Z#m$Z$m%Z%m&Z&m'Z'm(Z(m)Z)m*Z*m+Z+m,Z,m-Z-m.Z.m/Z/ d d
l0m1Z1 d dl2m3Z3m4Z4m5Z5 d dl6m7Z7 edddZ8e8duZ9da:ddddZ;e;ed G dd dZ<G dd dZ=dd!d"Z>dd#d$Z?	ddd'd(Z@dd.d/ZA			ddd4d5ZBdd6d7ZCddd9d:ZDdd=d>ZEddBdCZFddDdEZGddddFddGdHZHddddFddIdJZIe<dKeEeGddd ddLddPdQZJddWdXZKe<e1e= eEddddFddYdZZLe= ddddFdd[d\ZMddadbZNeOejPfddgdhZQe=didjdddiddkddldmZRe<dKdne=didjdddiddkddodpZSe<dKdndddiddkddqdrZTdsdt ZUeUdudvdwZVeUdxdydwZWe<dzddddFdd|d}ZXe<dzddddFdd~dZYe<dKdneGddddFdddZZe<dKdneGddddFdddZ[e<dKdneGddd ddLdddZ\dddZ]eOejPfdddZ^	iddddZ_dddZ`dd Zae<dKdnddddddZbdddZce<dKdnddiddddZddd Zedd ZfefejgZhefejiZjefejkZlefejmZnefejoZpefejqZrdddZsdS )    )annotationsN)AnyCallablecast)
get_option)NaTNaTTypeiNaTlib)		ArrayLikeAxisIntCorrelationMethodDtypeDtypeObjFScalarShapenpt)import_optional_dependency)find_stack_level)is_any_int_dtypeis_bool_dtype
is_complexis_datetime64_any_dtypeis_floatis_float_dtype
is_integeris_integer_dtypeis_numeric_dtypeis_object_dtype	is_scalaris_timedelta64_dtypeneeds_i8_conversionpandas_dtype)PeriodDtype)isnana_value_for_dtypenotna)extract_arrayZ
bottleneckwarn)errorsFTvboolreturnNonec                 C  s   t r| ad S d S N)_BOTTLENECK_INSTALLED_USE_BOTTLENECK)r+    r2   F/app/.heroku/python/lib/python3.10/site-packages/pandas/core/nanops.pyset_use_bottleneckC   s   r4   zcompute.use_bottleneckc                      s2   e Zd Zd fddZddd	ZdddZ  ZS )disallowdtypesr   r-   r.   c                   s"   t    tdd |D | _d S )Nc                 s  s    | ]}t |jV  qd S r/   )r#   type).0dtyper2   r2   r3   	<genexpr>P       z$disallow.__init__.<locals>.<genexpr>)super__init__tupler6   )selfr6   	__class__r2   r3   r=   N   s   
zdisallow.__init__r,   c                 C  s   t |dot|jj| jS )Nr9   )hasattr
issubclassr9   r7   r6   )r?   objr2   r2   r3   checkR   s   zdisallow.checkfr   c                   s"   t   fdd}tt|S )Nc               
     s   t | | }tfdd|D r" jdd}td| dz!tjdd  | i |W  d    W S 1 s<w   Y  W d S  t	y[ } zt
| d	 rVt|| d }~ww )
Nc                 3  s    | ]}  |V  qd S r/   )rE   )r8   rD   )r?   r2   r3   r:   Y   r;   z0disallow.__call__.<locals>._f.<locals>.<genexpr>nan zreduction operation 'z' not allowed for this dtypeignoreinvalidr   )	itertoolschainvaluesany__name__replace	TypeErrornperrstate
ValueErrorr   )argskwargsZobj_iterf_nameerF   r?   r2   r3   _fV   s    
(
zdisallow.__call__.<locals>._f	functoolswrapsr   r   )r?   rF   r[   r2   rZ   r3   __call__U   s   
zdisallow.__call__)r6   r   r-   r.   r-   r,   )rF   r   r-   r   )rP   
__module____qualname__r=   rE   r_   __classcell__r2   r2   r@   r3   r5   M   s    
r5   c                   @  s"   e Zd Zd
dddZddd	ZdS )bottleneck_switchNr-   r.   c                 K  s   || _ || _d S r/   )namerW   )r?   re   rW   r2   r2   r3   r=   n   s   
zbottleneck_switch.__init__altr   c              	     sf   j p jzttW n ttfy   d Y nw t d ddd fd	d
}tt	|S )NTaxisskipnarN   
np.ndarrayrh   AxisInt | Noneri   r,   c                  s   t jdkrj D ]\}}||vr|||< q| jdkr*|dd u r*t| |S trj|rjt| jrj|dd d u r]|	dd  | fd|i|}t
|r[ | f||d|}|S  | f||d|}|S  | f||d|}|S )Nr   	min_countmaskrh   rg   )lenrW   itemssizeget_na_for_min_countr1   _bn_ok_dtyper9   pop	_has_infs)rN   rh   ri   kwdskr+   resultrf   Zbn_funcZbn_namer?   r2   r3   rF   z   s$   
z%bottleneck_switch.__call__.<locals>.f)rN   rj   rh   rk   ri   r,   )
re   rP   getattrbnAttributeError	NameErrorr]   r^   r   r   )r?   rf   rF   r2   ry   r3   r_   r   s   
'zbottleneck_switch.__call__r/   )r-   r.   )rf   r   r-   r   )rP   ra   rb   r=   r_   r2   r2   r2   r3   rd   m   s    rd   r9   r   re   strc                 C  s   t | st| s|dvS dS )N)nansumnanprodnanmeanF)r   r"   )r9   re   r2   r2   r3   rs      s   rs   c              	   C  sP   t | tjr| jdv rt| dS zt|  W S  t	t
fy'   Y dS w )N)f8Zf4KF)
isinstancerS   ndarrayr9   r
   Zhas_infsZravelisinfrO   rR   NotImplementedError)rx   r2   r2   r3   ru      s   
ru   
fill_valueScalar | Nonec                 C  sJ   |dur|S t | r|du rtjS |dkrtjS tj S |dkr#tjS tS )z9return the correct fill value for the dtype of the valuesN+inf)_na_ok_dtyperS   rG   infr
   i8maxr	   )r9   r   fill_value_typr2   r2   r3   _get_fill_value   s   r   rN   rj   ri   rm   npt.NDArray[np.bool_] | Nonec                 C  s:   |du rt | jst| jrdS |st| jrt| }|S )a  
    Compute a mask if and only if necessary.

    This function will compute a mask iff it is necessary. Otherwise,
    return the provided mask (potentially None) when a mask does not need to be
    computed.

    A mask is never necessary if the values array is of boolean or integer
    dtypes, as these are incapable of storing NaNs. If passing a NaN-capable
    dtype that is interpretable as either boolean or integer data (eg,
    timedelta64), a mask must be provided.

    If the skipna parameter is False, a new mask will not be computed.

    The mask is computed using isna() by default. Setting invert=True selects
    notna() as the masking function.

    Parameters
    ----------
    values : ndarray
        input array to potentially compute mask for
    skipna : bool
        boolean for whether NaNs should be skipped
    mask : Optional[ndarray]
        nan-mask if known

    Returns
    -------
    Optional[np.ndarray[bool]]
    N)r   r9   r   r"   r%   )rN   ri   rm   r2   r2   r3   _maybe_get_mask   s   !r   r   r   
str | NoneHtuple[np.ndarray, npt.NDArray[np.bool_] | None, np.dtype, np.dtype, Any]c           	      C  s   t |sJ t| dd} t| ||}| j}d}t| jr&t| d} d}t|}t	|||d}|rW|durW|durW|
 rW|sC|rO|  } t| || nt| | |} |}t|sat|rhttj}n
t|rrttj}| ||||fS )a7  
    Utility to get the values view, mask, dtype, dtype_max, and fill_value.

    If both mask and fill_value/fill_value_typ are not None and skipna is True,
    the values array will be copied.

    For input arrays of boolean or integer dtypes, copies will only occur if a
    precomputed mask, a fill_value/fill_value_typ, and skipna=True are
    provided.

    Parameters
    ----------
    values : ndarray
        input array to potentially compute mask for
    skipna : bool
        boolean for whether NaNs should be skipped
    fill_value : Any
        value to fill NaNs with
    fill_value_typ : str
        Set to '+inf' or '-inf' to handle dtype-specific infinities
    mask : Optional[np.ndarray[bool]]
        nan-mask if known

    Returns
    -------
    values : ndarray
        Potential copy of input value array
    mask : Optional[ndarray[bool]]
        Mask for values, if deemed necessary to compute
    dtype : np.dtype
        dtype for values
    dtype_max : np.dtype
        platform independent dtype
    fill_value : Any
        fill value used
    TZextract_numpyFi8)r   r   N)r    r(   r   r9   r"   rS   Zasarrayviewr   r   rO   copyputmaskwherer   r   int64r   float64)	rN   ri   r   r   rm   r9   datetimelikeZdtype_ok	dtype_maxr2   r2   r3   _get_values  s0   .
r   c                 C  s   t | rdS t| jtj S )NF)r"   rC   r7   rS   integerr9   r2   r2   r3   r   a  s   r   np.dtypec                 C  s  | t u r	 | S t|rL|du rt}t| tjsEt|rJ d| |kr&tj} t| r4tdd	|} nt
| |} | j	|dd} | S | 	|} | S t|rt| tjs| |ks_t| ritd	|} | S t| tjkrutdt
| j	|dd} | S | 	d|} | S )	zwrap our results if neededNzExpected non-null fill_valuer   nsFr   zoverflow in timedelta operationm8[ns])r   r   r	   r   rS   r   r%   rG   Z
datetime64astyper   r   r!   isnanZtimedelta64fabsr
   r   rU   )rx   r9   r   r2   r2   r3   _wrap_resultsg  s8   #
r   funcr   c                   s,   t  ddddd fdd}tt|S )z
    If we have datetime64 or timedelta64 values, ensure we have a correct
    mask before calling the wrapped function, then cast back afterwards.
    NTrh   ri   rm   rN   rj   rh   rk   ri   r,   rm   r   c                  sr   | }| j jdv }|r|d u rt| } | f|||d|}|r7t||j td}|s7|d us0J t||||}|S )NmMr   )r   )r9   kindr%   r   r	   _mask_datetimelike_result)rN   rh   ri   rm   rW   orig_valuesr   rx   r   r2   r3   new_func  s   	z&_datetimelike_compat.<locals>.new_func)rN   rj   rh   rk   ri   r,   rm   r   r\   )r   r   r2   r   r3   _datetimelike_compat  s   
r   rh   rk   Scalar | np.ndarrayc                 C  sh   t | r	| d} t| j}| jdkr|S |du r|S | jd| | j|d d  }tj||| jdS )a  
    Return the missing value for `values`.

    Parameters
    ----------
    values : ndarray
    axis : int or None
        axis for the reduction, required if values.ndim > 1.

    Returns
    -------
    result : scalar or ndarray
        For 1-D values, returns a scalar of the correct missing type.
        For 2-D values, returns a 1-D array where each element is missing.
    r      Nr   )r   r   r&   r9   ndimshaperS   full)rN   rh   r   Zresult_shaper2   r2   r3   rr     s   


 rr   c                   s(   t  ddd	 fdd}tt|S )
z
    NumPy operations on C-contiguous ndarrays with axis=1 can be
    very slow if axis 1 >> axis 0.
    Operate row-by-row and concatenate the results.
    Nrh   rN   rj   rh   rk   c                  s   |dkrT| j dkrT| jd rT| jd d | jd krT| jtkrT| jtkrTt|  dd urEd fddt	t
 D }n
fd	d D }t|S | fd
|iS )Nr      ZC_CONTIGUOUSi  r   rm   c                   s(   g | ]} | fd | iqS rm   r2   )r8   i)arrsr   rW   rm   r2   r3   
<listcomp>  s    z:maybe_operate_rowwise.<locals>.newfunc.<locals>.<listcomp>c                   s   g | ]
} |fi qS r2   r2   )r8   x)r   rW   r2   r3   r     s    rh   )r   flagsr   r9   objectr,   listrq   rt   rangern   rS   array)rN   rh   rW   resultsr   )r   rW   rm   r3   newfunc  s*   



z&maybe_operate_rowwise.<locals>.newfunc)rN   rj   rh   rk   r\   )r   r   r2   r   r3   maybe_operate_rowwise  s   
r   r   c                C  ^   t | jr| jjdkrtjdtt d t| |d|d\} }}}}t| r*| 	t
} | |S )a  
    Check if any elements along an axis evaluate to True.

    Parameters
    ----------
    values : ndarray
    axis : int, optional
    skipna : bool, default True
    mask : ndarray[bool], optional
        nan-mask if known

    Returns
    -------
    result : bool

    Examples
    --------
    >>> from pandas.core import nanops
    >>> s = pd.Series([1, 2])
    >>> nanops.nanany(s)
    True

    >>> from pandas.core import nanops
    >>> s = pd.Series([np.nan])
    >>> nanops.nanany(s)
    False
    r   zz'any' with datetime64 dtypes is deprecated and will raise in a future version. Use (obj != pd.Timestamp(0)).any() instead.
stacklevelFr   rm   )r"   r9   r   warningsr)   FutureWarningr   r   r   r   r,   rO   rN   rh   ri   rm   _r2   r2   r3   nanany     "

r   c                C  r   )a  
    Check if all elements along an axis evaluate to True.

    Parameters
    ----------
    values : ndarray
    axis : int, optional
    skipna : bool, default True
    mask : ndarray[bool], optional
        nan-mask if known

    Returns
    -------
    result : bool

    Examples
    --------
    >>> from pandas.core import nanops
    >>> s = pd.Series([1, 2, np.nan])
    >>> nanops.nanall(s)
    True

    >>> from pandas.core import nanops
    >>> s = pd.Series([1, 0])
    >>> nanops.nanall(s)
    False
    r   zz'all' with datetime64 dtypes is deprecated and will raise in a future version. Use (obj != pd.Timestamp(0)).all() instead.r   Tr   )r"   r9   r   r   r)   r   r   r   r   r   r,   allr   r2   r2   r3   nanall*  r   r   ZM8)rh   ri   rl   rm   rl   intfloatc          
      C  sf   t | |d|d\} }}}}|}t|r|}n
t|r ttj}| j||d}	t|	||| j|d}	|	S )a  
    Sum the elements along an axis ignoring NaNs

    Parameters
    ----------
    values : ndarray[dtype]
    axis : int, optional
    skipna : bool, default True
    min_count: int, default 0
    mask : ndarray[bool], optional
        nan-mask if known

    Returns
    -------
    result : dtype

    Examples
    --------
    >>> from pandas.core import nanops
    >>> s = pd.Series([1, 2, np.nan])
    >>> nanops.nansum(s)
    3.0
    r   r   r   rl   )	r   r   r!   rS   r9   r   sum_maybe_null_outr   )
rN   rh   ri   rl   rm   r9   r   r   	dtype_sumthe_sumr2   r2   r3   r   a  s   "r   rx   +np.ndarray | np.datetime64 | np.timedelta64npt.NDArray[np.bool_]r   5np.ndarray | np.datetime64 | np.timedelta64 | NaTTypec                 C  sT   t | tjr| d|j} |j|d}t| |< | S | r(tt|jS | S )Nr   r   )	r   rS   r   r   r   r9   rO   r	   r   )rx   rh   rm   r   Z	axis_maskr2   r2   r3   r     s   r   c                C  s  t | |d|d\} }}}}|}ttj}|jdv r!ttj}nt|r,ttj}nt|r4|}|}t| j|||d}	t	| j
||d}
|durt|
ddrttj|	}	tjdd	 |
|	 }W d   n1 skw   Y  |	dk}| r}tj||< |S |	dkr|
|	 ntj}|S )
a  
    Compute the mean of the element along an axis ignoring NaNs

    Parameters
    ----------
    values : ndarray
    axis : int, optional
    skipna : bool, default True
    mask : ndarray[bool], optional
        nan-mask if known

    Returns
    -------
    float
        Unless input is a float array, in which case use the same
        precision as the input array.

    Examples
    --------
    >>> from pandas.core import nanops
    >>> s = pd.Series([1, 2, np.nan])
    >>> nanops.nanmean(s)
    1.5
    r   r   r   r   Nr   FrI   r   )r   rS   r9   r   r   r   r   _get_countsr   _ensure_numericr   rz   r   r   rT   rO   rG   )rN   rh   ri   rm   r9   r   r   r   Zdtype_countcountr   Zthe_meanZct_maskr2   r2   r3   r     s2   "


r   c          
   
     s"  d
 fdd	}t |  |dd\} }}}}t| js4z| d} W n ty3 } ztt||d}~ww |dur=tj| |< | j	}| j
dkr|dur|rw sUt||| }	n7t  tdd	t t| |}	W d   n1 sqw   Y  nt| j|tjtj}	n
|r|| |ntj}	t|	|S )a  
    Parameters
    ----------
    values : ndarray
    axis : int, optional
    skipna : bool, default True
    mask : ndarray[bool], optional
        nan-mask if known

    Returns
    -------
    result : float
        Unless input is a float array, in which case use the same
        precision as the input array.

    Examples
    --------
    >>> from pandas.core import nanops
    >>> s = pd.Series([1, np.nan, 2, 2])
    >>> nanops.nanmedian(s)
    2.0
    Nc                   st   |d u r	t | }n| } s| stjS t  tddt t| | }W d    |S 1 s3w   Y  |S )NrI   All-NaN slice encountered)	r'   r   rS   rG   r   catch_warningsfilterwarningsRuntimeWarning	nanmedian)r   Z_maskresri   r2   r3   
get_median   s   


znanmedian.<locals>.get_medianr   )rm   r   r   r   rI   r   r/   )r   r   r9   r   rU   rR   r~   rS   rG   rp   r   Zapply_along_axisr   r   r   r   r   get_empty_reduction_resultr   Zfloat_r   )
rN   rh   ri   rm   r   r9   r   errZnotemptyr   r2   r   r3   r     s4   



r   r   tuple[int, ...]r   np.dtype | type[np.floating]c                 C  s<   t | }t t| }t j|||k |d}|| |S )z
    The result from a reduction on an empty ndarray.

    Parameters
    ----------
    shape : Tuple[int]
    axis : int
    dtype : np.dtype
    fill_value : Any

    Returns
    -------
    np.ndarray
    r   )rS   r   Zarangern   emptyfill)r   rh   r9   r   Zshpdimsretr2   r2   r3   r   8  s
   

r   values_shaper   ddof-tuple[float | np.ndarray, float | np.ndarray]c                 C  s   t | |||d}||| }t|r!||krtj}tj}||fS ttj|}||k}| r?t||tj t||tj ||fS )a:  
    Get the count of non-null values along an axis, accounting
    for degrees of freedom.

    Parameters
    ----------
    values_shape : Tuple[int, ...]
        shape tuple from values ndarray, used if mask is None
    mask : Optional[ndarray[bool]]
        locations in values that should be considered missing
    axis : Optional[int]
        axis to count along
    ddof : int
        degrees of freedom
    dtype : type, optional
        type to use for count

    Returns
    -------
    count : int, np.nan or np.ndarray
    d : int, np.nan or np.ndarray
    r   )	r   r7   r    rS   rG   r   r   rO   r   )r   rm   rh   r   r9   r   dr2   r2   r3   _get_counts_nanvarS  s   r   r   r   rh   ri   r   rm   c             	   C  sT   | j dkr
| d} | j }t| ||d\} }}}}tt| ||||d}t||S )a  
    Compute the standard deviation along given axis while ignoring NaNs

    Parameters
    ----------
    values : ndarray
    axis : int, optional
    skipna : bool, default True
    ddof : int, default 1
        Delta Degrees of Freedom. The divisor used in calculations is N - ddof,
        where N represents the number of elements.
    mask : ndarray[bool], optional
        nan-mask if known

    Returns
    -------
    result : float
        Unless input is a float array, in which case use the same
        precision as the input array.

    Examples
    --------
    >>> from pandas.core import nanops
    >>> s = pd.Series([1, np.nan, 2, 3])
    >>> nanops.nanstd(s)
    1.0
    zM8[ns]r   r   r   )r9   r   r   rS   sqrtnanvarr   )rN   rh   ri   r   rm   Z
orig_dtyper   rx   r2   r2   r3   nanstd  s   
$

r   Zm8c                C  s  t | dd} | j}t| ||}t|r!| d} |dur!tj| |< t| jr3t| j	|||| j\}}n
t| j	|||\}}|rN|durN| 
 } t| |d t| j|tjd| }|durdt||}t||  d }	|durwt|	|d |	j|tjd| }
t|r|
j|dd	}
|
S )
a  
    Compute the variance along given axis while ignoring NaNs

    Parameters
    ----------
    values : ndarray
    axis : int, optional
    skipna : bool, default True
    ddof : int, default 1
        Delta Degrees of Freedom. The divisor used in calculations is N - ddof,
        where N represents the number of elements.
    mask : ndarray[bool], optional
        nan-mask if known

    Returns
    -------
    result : float
        Unless input is a float array, in which case use the same
        precision as the input array.

    Examples
    --------
    >>> from pandas.core import nanops
    >>> s = pd.Series([1, np.nan, 2, 3])
    >>> nanops.nanvar(s)
    1.0
    Tr   r   Nr   )rh   r9   r   Fr   )r(   r9   r   r   r   rS   rG   r   r   r   r   r   r   r   r   expand_dims)rN   rh   ri   r   rm   r9   r   r   ZavgZsqrrx   r2   r2   r3   r     s.   %


r   c                C  s   t | ||||d t| ||}t| js| d} |s&|dur&| r&tjS t| j	|||| j\}}t | ||||d}t
|t
| S )a  
    Compute the standard error in the mean along given axis while ignoring NaNs

    Parameters
    ----------
    values : ndarray
    axis : int, optional
    skipna : bool, default True
    ddof : int, default 1
        Delta Degrees of Freedom. The divisor used in calculations is N - ddof,
        where N represents the number of elements.
    mask : ndarray[bool], optional
        nan-mask if known

    Returns
    -------
    result : float64
        Unless input is a float array, in which case use the same
        precision as the input array.

    Examples
    --------
    >>> from pandas.core import nanops
    >>> s = pd.Series([1, np.nan, 2, 3])
    >>> nanops.nansem(s)
     0.5773502691896258
    r   r   N)r   r   r   r9   r   rO   rS   rG   r   r   r   )rN   rh   ri   r   rm   r   r   varr2   r2   r3   nansem  s   &

r   c                   s2   t d dtd dd dd fdd}|S )NrG   )re   Tr   rN   rj   rh   rk   ri   r,   rm   r   r-   r   c             
     s   t | | |d\} }}}}|d ur| j| dks| jdkr>zt| ||d}|tj W n ttt	fy=   tj}Y nw t| |}t
|||| j}|S )Nr   rm   r   r   )r   r   rp   rz   r   rS   rG   r|   rR   rU   r   )rN   rh   ri   rm   r9   r   r   rx   r   methr2   r3   	reduction2  s   	 
z_nanminmax.<locals>.reduction)
rN   rj   rh   rk   ri   r,   rm   r   r-   r   )rd   r   )r  r   r  r2   r   r3   
_nanminmax1  s   r  minr   )r   max-infOint | np.ndarrayc                C  6   t | dd|d\} }}}}| |}t||||}|S )a  
    Parameters
    ----------
    values : ndarray
    axis : int, optional
    skipna : bool, default True
    mask : ndarray[bool], optional
        nan-mask if known

    Returns
    -------
    result : int or ndarray[int]
        The index/indices  of max value in specified axis or -1 in the NA case

    Examples
    --------
    >>> from pandas.core import nanops
    >>> arr = np.array([1, 2, 3, np.nan, 4])
    >>> nanops.nanargmax(arr)
    4

    >>> arr = np.array(range(12), dtype=np.float64).reshape(4, 3)
    >>> arr[2:, 2] = np.nan
    >>> arr
    array([[ 0.,  1.,  2.],
           [ 3.,  4.,  5.],
           [ 6.,  7., nan],
           [ 9., 10., nan]])
    >>> nanops.nanargmax(arr, axis=1)
    array([2, 2, 1, 1])
    Tr  r   )r   Zargmax_maybe_arg_null_outrN   rh   ri   rm   r   rx   r2   r2   r3   	nanargmaxR     '
r  c                C  r	  )a  
    Parameters
    ----------
    values : ndarray
    axis : int, optional
    skipna : bool, default True
    mask : ndarray[bool], optional
        nan-mask if known

    Returns
    -------
    result : int or ndarray[int]
        The index/indices of min value in specified axis or -1 in the NA case

    Examples
    --------
    >>> from pandas.core import nanops
    >>> arr = np.array([1, 2, 3, np.nan, 4])
    >>> nanops.nanargmin(arr)
    0

    >>> arr = np.array(range(12), dtype=np.float64).reshape(4, 3)
    >>> arr[2:, 0] = np.nan
    >>> arr
    array([[ 0.,  1.,  2.],
           [ 3.,  4.,  5.],
           [nan,  7.,  8.],
           [nan, 10., 11.]])
    >>> nanops.nanargmin(arr, axis=1)
    array([0, 0, 1, 1])
    Tr   r   )r   Zargminr
  r  r2   r2   r3   	nanargmin  r  r  c                C  s  t | dd} t| ||}t| js| d} t| j||}n
t| j||| jd}|r:|dur:|  } t	| |d n|sG|durG|
 rGtjS | j|tjd| }|dur[t||}| | }|rl|durlt	||d |d }|| }|j|tjd}	|j|tjd}
t|	}	t|
}
tjddd	 ||d
 d  |d  |
|	d   }W d   n1 sw   Y  | j}t|r|j|dd}t|tjrt|	dkd|}tj||dk < |S |	dkrdn|}|dk rtjS |S )a  
    Compute the sample skewness.

    The statistic computed here is the adjusted Fisher-Pearson standardized
    moment coefficient G1. The algorithm computes this coefficient directly
    from the second and third central moment.

    Parameters
    ----------
    values : ndarray
    axis : int, optional
    skipna : bool, default True
    mask : ndarray[bool], optional
        nan-mask if known

    Returns
    -------
    result : float64
        Unless input is a float array, in which case use the same
        precision as the input array.

    Examples
    --------
    >>> from pandas.core import nanops
    >>> s = pd.Series([1, np.nan, 1, 2])
    >>> nanops.nanskew(s)
    1.7320508075688787
    Tr   r   r   Nr   r   rI   rK   divider   g      ?g      ?Fr      )r(   r   r   r9   r   r   r   r   rS   r   rO   rG   r   r   r   _zero_out_fperrrT   r   r   r   )rN   rh   ri   rm   r   meanadjusted	adjusted2Z	adjusted3m2Zm3rx   r9   r2   r2   r3   nanskew  sJ   '

&r  c                C  sF  t | dd} t| ||}t| js| d} t| j||}n
t| j||| jd}|r:|dur:|  } t	| |d n|sG|durG|
 rGtjS | j|tjd| }|dur[t||}| | }|rl|durlt	||d |d }|d }|j|tjd}	|j|tjd}
tjddd	0 d
|d d  |d |d
   }||d  |d  |
 }|d |d
  |	d  }W d   n1 sw   Y  t|}t|}t|tjs|dk rtjS |dkrdS tjddd	 || | }W d   n1 sw   Y  | j}t|r
|j|dd}t|tjr!t|dkd|}tj||dk < |S )a  
    Compute the sample excess kurtosis

    The statistic computed here is the adjusted Fisher-Pearson standardized
    moment coefficient G2, computed directly from the second and fourth
    central moment.

    Parameters
    ----------
    values : ndarray
    axis : int, optional
    skipna : bool, default True
    mask : ndarray[bool], optional
        nan-mask if known

    Returns
    -------
    result : float64
        Unless input is a float array, in which case use the same
        precision as the input array.

    Examples
    --------
    >>> from pandas.core import nanops
    >>> s = pd.Series([1, np.nan, 1, 3, 2])
    >>> nanops.nankurt(s)
    -1.2892561983471076
    Tr   r   r   Nr   r   rI   r  r  r      Fr   )r(   r   r   r9   r   r   r   r   rS   r   rO   rG   r   r   r   rT   r  r   r   r   )rN   rh   ri   rm   r   r  r  r  Z	adjusted4r  Zm4Zadj	numeratordenominatorrx   r9   r2   r2   r3   nankurt  sV   '

 	
r  c                C  sF   t | ||}|r|dur|  } d| |< | |}t|||| j|dS )a  
    Parameters
    ----------
    values : ndarray[dtype]
    axis : int, optional
    skipna : bool, default True
    min_count: int, default 0
    mask : ndarray[bool], optional
        nan-mask if known

    Returns
    -------
    Dtype
        The product of all elements on a given axis. ( NaNs are treated as 1)

    Examples
    --------
    >>> from pandas.core import nanops
    >>> s = pd.Series([1, 2, 3, np.nan])
    >>> nanops.nanprod(s)
    6.0
    Nr   r   )r   r   prodr   r   )rN   rh   ri   rl   rm   rx   r2   r2   r3   r   k  s    
r   np.ndarray | intc                 C  sr   |d u r| S |d u st | dds"|r| rdS | S | r dS | S |r*||}n||}| r7d| |< | S )Nr   F)rz   r   rO   )rx   rh   rm   ri   Zna_maskr2   r2   r3   r
    s    
r
  float | np.ndarrayc                 C  sz   |du r|dur|j |  }nt| }||S |dur)|j| || }n| | }t|r6||S |j|ddS )a  
    Get the count of non-null values along an axis

    Parameters
    ----------
    values_shape : tuple of int
        shape tuple from values ndarray, used if mask is None
    mask : Optional[ndarray[bool]]
        locations in values that should be considered missing
    axis : Optional[int]
        axis to count along
    dtype : type, optional
        type to use for count

    Returns
    -------
    count : scalar or array
    NFr   )rp   r   rS   r  r7   r   r    r   )r   rm   rh   r9   nr   r2   r2   r3   r     s   


r   np.ndarray | float | NaTTypec           	      C  s  |du r
|dkr
| S |durot | tjro|dur'|j| || | dk }n|| | dk }|d| ||d d  }t||}t|rmt| rit| rW| 	d} nt
| sb| j	ddd} tj| |< | S d| |< | S | turt|||rt| dd}t
|r|d	} | S tj} | S )
zu
    Returns
    -------
    Dtype
        The product of all elements on a given axis. ( NaNs are treated as 1)
    Nr   r   Zc16r   Fr   r9   rG   )r   rS   r   r   r   Zbroadcast_torO   r   Ziscomplexobjr   r   rG   r   check_below_min_countrz   r7   )	rx   rh   rm   r   rl   Z	null_maskZbelow_countZ	new_shapeZresult_dtyper2   r2   r3   r     s4   




r   c                 C  s:   |dkr|du rt | }n|j|  }||k rdS dS )a  
    Check for the `min_count` keyword. Returns True if below `min_count` (when
    missing value should be returned from the reduction).

    Parameters
    ----------
    shape : tuple
        The shape of the values (`values.shape`).
    mask : ndarray[bool] or None
        Boolean numpy array (typically of same shape as `shape`) or None.
    min_count : int
        Keyword passed through from sum/prod call.

    Returns
    -------
    bool
    r   NTF)rS   r  rp   r   )r   rm   rl   Z	non_nullsr2   r2   r3   r"    s   r"  c                 C  sr   t | tjr*tjdd tt| dk d| W  d    S 1 s#w   Y  d S t| dk r7| jdS | S )NrI   rJ   g+=r   )r   rS   r   rT   r   absr9   r7   )argr2   r2   r3   r  +  s
   $r  pearson)methodmin_periodsabr&  r   r'  
int | Nonec                C  sp   t | t |krtd|du rd}t| t|@ }| s&| | } || }t | |k r/tjS t|}|| |S )z
    a, b: ndarrays
    z'Operands to nancorr must have same sizeNr   )rn   AssertionErrorr'   r   rS   rG   get_corr_func)r(  r)  r&  r'  validrF   r2   r2   r3   nancorr4  s   
r.  )Callable[[np.ndarray, np.ndarray], float]c                   sx   | dkrddl m   fdd}|S | dkr$ddl m fdd}|S | d	kr.d
d }|S t| r4| S td|  d)NZkendallr   
kendalltauc                       | |d S Nr   r2   r(  r)  r0  r2   r3   r   W     zget_corr_func.<locals>.funcZspearman	spearmanrc                   r2  r3  r2   r4  r6  r2   r3   r   ^  r5  r%  c                 S  s   t | |d S )Nr   r   )rS   Zcorrcoefr4  r2   r2   r3   r   d  s   zUnknown method 'z@', expected one of 'kendall', 'spearman', 'pearson', or callable)Zscipy.statsr1  r7  callablerU   )r&  r   r2   )r1  r7  r3   r,  Q  s    
r,  )r'  r   c                C  sr   t | t |krtd|d u rd}t| t|@ }| s&| | } || }t | |k r/tjS tj| ||dd S )Nz&Operands to nancov must have same sizer   r   r8  )rn   r+  r'   r   rS   rG   Zcov)r(  r)  r'  r   r-  r2   r2   r3   nancovq  s   r:  c                 C  s,  t | tjrYt| st| r| tj} | S t| rWz| tj} W n) t	t
fyK   z
| tj} W Y | S  t
yJ } z	t	d|  d|d }~ww w tt| sW| j} | S t| st| st| szt| } W | S  t	t
fy   zt| } W Y | S  t
y } z	t	d|  d|d }~ww w | S )NzCould not convert z to numeric)r   rS   r   r   r   r   r   r   Z
complex128rR   rU   rO   imagrealr   r   r   r   complex)r   r   r2   r2   r3   r     sB   
r   c                   s    fdd}|S )Nc                   s|   t | }t |}||B }tjdd  | |}W d    n1 s"w   Y  | r<t|r4|d}t||tj |S )NrI   r   r  )r%   rS   rT   rO   r   r   r   rG   )r   yZxmaskZymaskrm   rx   opr2   r3   rF     s   
zmake_nancomp.<locals>.fr2   )r@  rF   r2   r?  r3   make_nancomp  s   rA  r   c             	   C  s   t jdt jft jjt j t jft jdt jft jjt jt jfi| \}}| jj	dvs+J |rPt
| jjt jt jfsP|  }t|}|||< ||dd}|||< |S || dd}|S )a  
    Cumulative function with skipna support.

    Parameters
    ----------
    values : np.ndarray or ExtensionArray
    accum_func : {np.cumprod, np.maximum.accumulate, np.cumsum, np.minimum.accumulate}
    skipna : bool

    Returns
    -------
    np.ndarray or ExtensionArray
    g      ?g        r   r   r   )rS   ZcumprodrG   maximum
accumulater   Zcumsumminimumr9   r   rC   r7   r   Zbool_r   r%   )rN   Z
accum_funcri   Zmask_aZmask_bvalsrm   rx   r2   r2   r3   na_accum_func  s"   rF  )T)r+   r,   r-   r.   )r9   r   re   r~   r-   r,   r`   )NN)r9   r   r   r   )rN   rj   ri   r,   rm   r   r-   r   )NNN)rN   rj   ri   r,   r   r   r   r   rm   r   r-   r   )r9   r   r-   r,   r/   )r9   r   )r   r   r-   r   )rN   rj   rh   rk   r-   r   )
rN   rj   rh   rk   ri   r,   rm   r   r-   r,   )rN   rj   rh   rk   ri   r,   rl   r   rm   r   r-   r   )
rx   r   rh   rk   rm   r   r   rj   r-   r   )
rN   rj   rh   rk   ri   r,   rm   r   r-   r   )rh   rk   ri   r,   )
r   r   rh   r   r9   r   r   r   r-   rj   )r   r   rm   r   rh   rk   r   r   r9   r   r-   r   )rh   rk   ri   r,   r   r   )rN   rj   rh   rk   ri   r,   r   r   rm   r   r-   r   )
rN   rj   rh   rk   ri   r,   rm   r   r-   r  )
rx   rj   rh   rk   rm   r   ri   r,   r-   r  )
r   r   rm   r   rh   rk   r9   r   r-   r  )r   )rx   r!  rh   rk   rm   r   r   r   rl   r   r-   r!  )r   r   rm   r   rl   r   r-   r,   )
r(  rj   r)  rj   r&  r   r'  r*  r-   r   )r&  r   r-   r/  )
r(  rj   r)  rj   r'  r*  r   r*  r-   r   )rN   r   ri   r,   r-   r   )t
__future__r   r]   rL   operatortypingr   r   r   r   numpyrS   Zpandas._configr   Zpandas._libsr   r   r	   r
   Zpandas._typingr   r   r   r   r   r   r   r   r   Zpandas.compat._optionalr   Zpandas.util._exceptionsr   Zpandas.core.dtypes.commonr   r   r   r   r   r   r   r   r   r   r    r!   r"   r#   Zpandas.core.dtypes.dtypesr$   Zpandas.core.dtypes.missingr%   r&   r'   Zpandas.core.constructionr(   r{   r0   r1   r4   r5   rd   rs   ru   r   r   r   r   r   r   rr   r   r   r   r   r   r   r   r   r9   r   r   r   r   r   r  ZnanminZnanmaxr  r  r  r  r   r
  r   r   r"  r  r.  r,  r:  r   rA  gtZnangtgeZnangeltZnanltleZnanleeqZnaneqneZnannerF  r2   r2   r2   r3   <module>   s   ,@ 
8

/
Y
)
"
%:7
.?
P
 /-J4--Xa
+
.
0	
  





