
    Mpj                     >   S r SSKrSSKrSSKJr  SSKJrJrJ	r	J
r
JrJrJrJrJrJrJr  SSKJrJrJrJrJrJr  SSKJr  SSKJr  SSKJrJrJ r   SS	K!J"r"  SS
K#J$r$   " S S5      r% " S S\%5      r& " S S\%5      r' " S S\%5      r( " S S\%5      r) " S S\%5      r* " S S\%5      r+ " S S\%5      r, " S S\%5      r- " S S\%5      r. " S S \%5      r/ " S! S"\%5      r0\&\'\(\)\*\+\,\.\/\0S#.
r1 " S$ S%5      r2S& r3 " S' S(\2\.5      r4 " S) S*\2\/5      r5 " S+ S,\2\*5      r6g)-z
This module contains loss classes suitable for fitting.

It is not part of the public API.
Specific losses are used for regression, binary classification or multiclass
classification.
    Nxlogy)CyAbsoluteErrorCyExponentialLossCyHalfBinomialLossCyHalfGammaLossCyHalfMultinomialLossCyHalfPoissonLossCyHalfSquaredErrorCyHalfTweedieLossCyHalfTweedieLossIdentityCyHuberLossCyPinballLoss)HalfLogitLinkIdentityLinkInterval	LogitLinkLogLinkMultinomialLogit)one_hot)check_scalar)_average
_logsumexp_ravel)softmax)_weighted_percentilec                       \ rS rSrSrSrSrSS jrS rS r	   SS	 jr
    SS
 jr   SS jr    SS jrSS jrSS jrSS jr\R$                  S4S jrSrg)BaseLossM   a  Base class for a loss function of 1-dimensional targets.

Conventions:

    - y_true.shape = sample_weight.shape = (n_samples,)
    - y_pred.shape = raw_prediction.shape = (n_samples,)
    - If is_multiclass is true (multiclass classification), then
      y_pred.shape = raw_prediction.shape = (n_samples, n_classes)
      Note that this corresponds to the return value of decision_function.

y_true, y_pred, sample_weight and raw_prediction must either be all float64
or all float32.
gradient and hessian must be either both float64 or both float32.

Note that y_pred = link.inverse(raw_prediction).

Specific loss classes can inherit specific link classes to satisfy
BaseLink's abstractmethods.

Parameters
----------
closs: CyLossFunction
    For example, a CyLossFunction; hence the name "c"loss.
link : BaseLink
sample_weight : {None, ndarray}
    If sample_weight is None, the hessian might be constant.
n_classes : {None, int}
    The number of classes for classification, else None.
xp : module, default=None
    Array namespace module.
device : device, default=None
    A device object (see the "Device Support" section of the array API spec).

Attributes
----------
closs: CyLossFunction
    For example, a CyLossFunction; hence the name "c"loss.
link : BaseLink
n_classes : {None, int}
    The number of classes for classification, else None.
xp : module or None
    Array namespace module. Ignored by the Cython implementation.
device : device or None
    A device object. Ignored by the Cython implementation.
interval_y_true : Interval
    Valid interval for y_true
interval_y_pred : Interval
    Valid Interval for y_pred
differentiable : bool
    Indicates whether or not loss function is differentiable in
    raw_prediction everywhere.
approx_hessian : bool
    Indicates whether the hessian is approximated or exact. If,
    approximated, it should be larger or equal to the exact one.
constant_hessian : bool
    Indicates whether the hessian is one for this loss.
is_multiclass : bool
    Indicates whether n_classes > 2 is allowed.
TFNc                     Xl         X l        X0l        X@l        XPl        SU l        SU l        [        [        R                  * [        R                  SS5      U l
        U R                  R                  U l        g )NF)closslink	n_classesxpdeviceapprox_hessianconstant_hessianr   npinfinterval_y_trueinterval_y_pred)selfr!   r"   r#   r$   r%   s         N/var/www/html/pdf-tiff/venv/lib/python3.13/site-packages/sklearn/_loss/loss.py__init__BaseLoss.__init__   sZ    
	"# %'F#yy88    c                 8    U R                   R                  U5      $ zUReturn True if y is in the valid range of y_true.

Parameters
----------
y : ndarray
)r*   includesr,   ys     r-   in_y_true_rangeBaseLoss.in_y_true_range        ##,,Q//r0   c                 8    U R                   R                  U5      $ )zUReturn True if y is in the valid range of y_pred.

Parameters
----------
y : ndarray
)r+   r3   r4   s     r-   in_y_pred_rangeBaseLoss.in_y_pred_range   r8   r0   c                     Uc  [         R                  " U5      nUR                  S:X  a$  UR                  S   S:X  a  UR	                  S5      nU R
                  R                  UUUUUS9  U$ )a  Compute the pointwise loss value for each input.

Parameters
----------
y_true : C-contiguous array of shape (n_samples,)
    Observed, true target values.
raw_prediction : C-contiguous array of shape (n_samples,) or array of             shape (n_samples, n_classes)
    Raw prediction values (in link space).
sample_weight : None or C-contiguous array of shape (n_samples,)
    Sample weights.
loss_out : None or C-contiguous array of shape (n_samples,)
    A location into which the result is stored. If None, a new array
    might be created.
n_threads : int, default=1
    Might use openmp thread parallelism.

Returns
-------
loss : array of shape (n_samples,)
    Element-wise loss function.
      y_trueraw_predictionsample_weightloss_out	n_threads)r(   
empty_likendimshapesqueezer!   lossr,   r@   rA   rB   rC   rD   s         r-   rI   BaseLoss.loss   ss    < }}V,H!#(<(<Q(?1(D+33A6N

)' 	 	
 r0   c           	         UcO  Uc-  [         R                  " U5      n[         R                  " U5      nO@[         R                  " XR                  S9nO!Uc  [         R                  " X$R                  S9nUR                  S:X  a$  UR                  S   S:X  a  UR                  S5      nUR                  S:X  a$  UR                  S   S:X  a  UR                  S5      nU R                  R                  UUUUUUS9  XE4$ )a  Compute loss and gradient w.r.t. raw_prediction for each input.

Parameters
----------
y_true : C-contiguous array of shape (n_samples,)
    Observed, true target values.
raw_prediction : C-contiguous array of shape (n_samples,) or array of             shape (n_samples, n_classes)
    Raw prediction values (in link space).
sample_weight : None or C-contiguous array of shape (n_samples,)
    Sample weights.
loss_out : None or C-contiguous array of shape (n_samples,)
    A location into which the loss is stored. If None, a new array
    might be created.
gradient_out : None or C-contiguous array of shape (n_samples,) or array             of shape (n_samples, n_classes)
    A location into which the gradient is stored. If None, a new array
    might be created.
n_threads : int, default=1
    Might use openmp thread parallelism.

Returns
-------
loss : array of shape (n_samples,)
    Element-wise loss function.

gradient : array of shape (n_samples,) or (n_samples, n_classes)
    Element-wise gradients.
dtyper=   r>   )r@   rA   rB   rC   gradient_outrD   )r(   rE   rN   rF   rG   rH   r!   loss_gradient)r,   r@   rA   rB   rC   rO   rD   s          r-   rP   BaseLoss.loss_gradient   s    L #==0!}}^<==7I7IJ!==~~NL !#(<(<Q(?1(D+33A6N!l&8&8&;q&@'//2L

  )'% 	! 	
 %%r0   c                 B   Uc  [         R                  " U5      nUR                  S:X  a$  UR                  S   S:X  a  UR	                  S5      nUR                  S:X  a$  UR                  S   S:X  a  UR	                  S5      nU R
                  R                  UUUUUS9  U$ )a  Compute gradient of loss w.r.t raw_prediction for each input.

Parameters
----------
y_true : C-contiguous array of shape (n_samples,)
    Observed, true target values.
raw_prediction : C-contiguous array of shape (n_samples,) or array of             shape (n_samples, n_classes)
    Raw prediction values (in link space).
sample_weight : None or C-contiguous array of shape (n_samples,)
    Sample weights.
gradient_out : None or C-contiguous array of shape (n_samples,) or array             of shape (n_samples, n_classes)
    A location into which the result is stored. If None, a new array
    might be created.
n_threads : int, default=1
    Might use openmp thread parallelism.

Returns
-------
gradient : array of shape (n_samples,) or (n_samples, n_classes)
    Element-wise gradients.
r=   r>   )r@   rA   rB   rO   rD   )r(   rE   rF   rG   rH   r!   gradientr,   r@   rA   rB   rO   rD   s         r-   rS   BaseLoss.gradient  s    > ==8L !#(<(<Q(?1(D+33A6N!l&8&8&;q&@'//2L

)'% 	 	
 r0   c           	      B   UcG  Uc-  [         R                  " U5      n[         R                  " U5      nO0[         R                  " U5      nOUc  [         R                  " U5      nUR                  S:X  a$  UR                  S   S:X  a  UR	                  S5      nUR                  S:X  a$  UR                  S   S:X  a  UR	                  S5      nUR                  S:X  a$  UR                  S   S:X  a  UR	                  S5      nU R
                  R                  UUUUUUS9  XE4$ )aG  Compute gradient and hessian of loss w.r.t raw_prediction.

Parameters
----------
y_true : C-contiguous array of shape (n_samples,)
    Observed, true target values.
raw_prediction : C-contiguous array of shape (n_samples,) or array of             shape (n_samples, n_classes)
    Raw prediction values (in link space).
sample_weight : None or C-contiguous array of shape (n_samples,)
    Sample weights.
gradient_out : None or C-contiguous array of shape (n_samples,) or array             of shape (n_samples, n_classes)
    A location into which the gradient is stored. If None, a new array
    might be created.
hessian_out : None or C-contiguous array of shape (n_samples,) or array             of shape (n_samples, n_classes)
    A location into which the hessian is stored. If None, a new array
    might be created.
n_threads : int, default=1
    Might use openmp thread parallelism.

Returns
-------
gradient : arrays of shape (n_samples,) or (n_samples, n_classes)
    Element-wise gradients.

hessian : arrays of shape (n_samples,) or (n_samples, n_classes)
    Element-wise hessians.
r=   r>   )r@   rA   rB   rO   hessian_outrD   )r(   rE   rF   rG   rH   r!   gradient_hessian)r,   r@   rA   rB   rO   rW   rD   s          r-   rX   BaseLoss.gradient_hessianP  s   N "!}}^< mmN;!}}[9 --5K !#(<(<Q(?1(D+33A6N!l&8&8&;q&@'//2Lq [%6%6q%9Q%>%--a0K

##)'%# 	$ 	
 ((r0   c           
      N    [         R                  " U R                  UUSSUS9US9$ )a  Compute the weighted average loss.

Parameters
----------
y_true : C-contiguous array of shape (n_samples,)
    Observed, true target values.
raw_prediction : C-contiguous array of shape (n_samples,) or array of             shape (n_samples, n_classes)
    Raw prediction values (in link space).
sample_weight : None or C-contiguous array of shape (n_samples,)
    Sample weights.
n_threads : int, default=1
    Might use openmp thread parallelism.

Returns
-------
loss : float
    Mean or averaged loss function.
Nr?   weights)r(   averagerI   )r,   r@   rA   rB   rD   s        r-   __call__BaseLoss.__call__  s:    ( zzII-"#   "	
 		
r0   c                    [         R                  " XSS9nS[         R                  " UR                  5      R                  -  nU R
                  R                  [         R                  * :X  a  SnOKU R
                  R                  (       a  U R
                  R                  nOU R
                  R                  U-   nU R
                  R                  [         R                  :X  a  SnOKU R
                  R                  (       a  U R
                  R                  nOU R
                  R                  U-
  nUc  Uc  U R                  R                  U5      $ U R                  R                  [         R                  " X5U5      5      $ )a  Compute raw_prediction of an intercept-only model.

This can be used as initial estimates of predictions, i.e. before the
first iteration in fit.

Parameters
----------
y_true : array-like of shape (n_samples,)
    Observed, true target values.
sample_weight : None or array of shape (n_samples,)
    Sample weights.

Returns
-------
raw_prediction : numpy scalar or array of shape (n_classes,)
    Raw predictions of an intercept-only model.
r   r\   axis
   N)r(   r]   finforN   epsr+   lowr)   low_inclusivehighhigh_inclusiver"   clip)r,   r@   rB   y_predre   a_mina_maxs          r-   fit_intercept_onlyBaseLoss.fit_intercept_only  s   ( FB288FLL)---##w.E!!//((,,E((,,s2E$$.E!!00((--E((--3E=U]99>>&))99>>"''&"?@@r0   c                 .    [         R                  " U5      $ )a  Calculate term dropped in loss.

With this term added, the loss of perfect predictions is zero.

Parameters
----------
y_true : array-like of shape (n_samples,)
    Observed, true target values.

sample_weight : None or array of shape (n_samples,), default=None
    Sample weights.

Returns
-------
constant : ndarray of shape (n_samples,)
    Constant value to be added to raw predictions so that the loss
    of perfect predictions becomes zero.
)r(   
zeros_liker,   r@   rB   s      r-   constant_to_optimal_zero!BaseLoss.constant_to_optimal_zero  s    & }}V$$r0   Fc                 X   U[         R                  [         R                  4;  a  [        SU S35      eU R                  (       a  XR
                  4nOU4n[         R                  " XBUS9nU R                  (       a  [         R                  " SUS9nXV4$ [         R                  " XBUS9nXV4$ )a  Initialize arrays for gradients and hessians.

Unless hessians are constant, arrays are initialized with undefined values.

Parameters
----------
n_samples : int
    The number of samples, usually passed to `fit()`.
dtype : {np.float64, np.float32}, default=np.float64
    The dtype of the arrays gradient and hessian.
order : {'C', 'F'}, default='F'
    Order of the arrays gradient and hessian. The default 'F' makes the arrays
    contiguous along samples.

Returns
-------
gradient : C-contiguous array of shape (n_samples,) or array of shape             (n_samples, n_classes)
    Empty array (allocated but not initialized) to be used as argument
    gradient_out.
hessian : C-contiguous array of shape (n_samples,), array of shape
    (n_samples, n_classes) or shape (1,)
    Empty (allocated but not initialized) array to be used as argument
    hessian_out.
    If constant_hessian is True (e.g. `HalfSquaredError`), the array is
    initialized to ``1``.
zCValid options for 'dtype' are np.float32 and np.float64. Got dtype=z	 instead.)rG   rN   order)r>   )rG   rN   )	r(   float32float64
ValueErroris_multiclassr#   emptyr'   ones)r,   	n_samplesrN   rw   rG   rS   hessians          r-   init_gradient_and_hessian"BaseLoss.init_gradient_and_hessian  s    8 RZZ00"G9. 
 /ELE88%EB  
 ggD6G    hhUuEG  r0   )	r&   r!   r'   r%   r+   r*   r"   r#   r$   NNNNNr>   NNNr>   Nr>   N)__name__
__module____qualname____firstlineno____doc__differentiabler{   r.   r6   r:   rI   rP   rS   rX   r^   rn   rs   r(   ry   r   __static_attributes__ r0   r-   r   r   M   s    :J NM	900 +b =&F /j @)D
>(AT%* :<3 1!r0   r   c                   0   ^  \ rS rSrSrSU 4S jjrSrU =r$ )HalfSquaredErrori$  a  Half squared error with identity link, for regression.

Domain:
y_true and y_pred all real numbers

Link:
y_pred = raw_prediction

For a given sample x_i, half squared error is defined as::

    loss(x_i) = 0.5 * (y_true_i - raw_prediction_i)**2

The factor of 0.5 simplifies the computation of gradients and results in a
unit hessian (and is consistent with what is done in LightGBM). It is also
half the Normal distribution deviance.
c                 V   > [         TU ]  [        5       [        5       X#S9  US L U l        g )Nr!   r"   r$   r%   )superr.   r   r   r'   r,   rB   r$   r%   	__class__s       r-   r.   HalfSquaredError.__init__6  s0    $&\^ 	 	
 !. 5r0   )r'   r   r   r   r   r   r   r.   r   __classcell__r   s   @r-   r   r   $  s    "6 6r0   r   c                   >   ^  \ rS rSrSrSrSU 4S jjrSS jrSrU =r	$ )	AbsoluteErrori=  a  Absolute error with identity link, for regression.

Domain:
y_true and y_pred all real numbers

Link:
y_pred = raw_prediction

For a given sample x_i, the absolute error is defined as::

    loss(x_i) = |y_true_i - raw_prediction_i|

Note that the exact hessian = 0 almost everywhere (except at one point, therefore
differentiable = False). Optimization routines like in HGBT, however, need a
hessian > 0. Therefore, we assign 1.
Fc                 d   > [         TU ]  [        5       [        5       X#S9  SU l        US L U l        g )Nr   T)r   r.   r   r   r&   r'   r   s       r-   r.   AbsoluteError.__init__Q  s8    !#,.R 	 	
 # - 5r0   c                 J    Uc  [         R                  " USS9$ [        XS5      $ )}Compute raw_prediction of an intercept-only model.

This is the weighted median of the target, i.e. over the samples
axis=0.
r   rb   2   )r(   medianr   rr   s      r-   rn    AbsoluteError.fit_intercept_onlyX  s(      99V!,,'rBBr0   r&   r'   r   r   
r   r   r   r   r   r   r.   rn   r   r   r   s   @r-   r   r   =  s     " N6	C 	Cr0   r   c                   >   ^  \ rS rSrSrSrSU 4S jjrSS jrSrU =r	$ )	PinballLossid  a3  Quantile loss aka pinball loss, for regression.

Domain:
y_true and y_pred all real numbers
quantile in (0, 1)

Link:
y_pred = raw_prediction

For a given sample x_i, the pinball loss is defined as::

    loss(x_i) = rho_{quantile}(y_true_i - raw_prediction_i)

    rho_{quantile}(u) = u * (quantile - 1_{u<0})
                      = -u *(1 - quantile)  if u < 0
                         u * quantile       if u >= 0

Note: 2 * PinballLoss(quantile=0.5) equals AbsoluteError().

Note that the exact hessian = 0 almost everywhere (except at one point, therefore
differentiable = False). Optimization routines like in HGBT, however, need a
hessian > 0. Therefore, we assign 1.

Additional Attributes
---------------------
quantile : float
    The quantile level of the quantile to be estimated. Must be in range (0, 1).
Fc           	         > [        US[        R                  SSSS9  [        TU ]  [        [        U5      S9[        5       UUS9  SU l        US L U l	        g )	Nquantiler   r>   neithertarget_typemin_valmax_valinclude_boundaries)r   r   T)
r   numbersRealr   r.   r   floatr   r&   r'   )r,   rB   r   r$   r%   r   s        r-   r.   PinballLoss.__init__  sc    (	
 	x9	 	 	
 # - 5r0   c                     Uc-  [         R                  " USU R                  R                  -  SS9$ [	        XSU R                  R                  -  5      $ )r   d   r   r   )r(   
percentiler!   r   r   rr   s      r-   rn   PinballLoss.fit_intercept_only  sM      ==tzz/B/B)BKK'sTZZ-@-@'@ r0   r   )N      ?NNr   r   r   s   @r-   r   r   d  s    : N6$ r0   r   c                   @   ^  \ rS rSrSrSr SU 4S jjrSS jrSrU =r	$ )		HuberLossi  a  Huber loss, for regression.

Domain:
y_true and y_pred all real numbers
quantile in (0, 1)

Link:
y_pred = raw_prediction

For a given sample x_i, the Huber loss is defined as::

    loss(x_i) = 1/2 * abserr**2            if abserr <= delta
                delta * (abserr - delta/2) if abserr > delta

    abserr = |y_true_i - raw_prediction_i|
    delta = quantile(abserr, self.quantile)

Note: HuberLoss(quantile=1) equals HalfSquaredError and HuberLoss(quantile=0)
equals delta * (AbsoluteError() - delta/2).

Additional Attributes
---------------------
quantile : float
    The quantile level which defines the breaking point `delta` to distinguish
    between absolute error and squared error. Must be in range (0, 1).

 Reference
---------
.. [1] Friedman, J.H. (2001). :doi:`Greedy function approximation: A gradient
  boosting machine <10.1214/aos/1013203451>`.
  Annals of Statistics, 29, 1189-1232.
Fc           	         > [        US[        R                  SSSS9  X l        [        TU ]  [        [        U5      S9[        5       UUS9  SU l	        S	U l
        g )
Nr   r   r>   r   r   )deltar   TF)r   r   r   r   r   r.   r   r   r   r&   r'   )r,   rB   r   r   r$   r%   r   s         r-   r.   HuberLoss.__init__  se     	(	
 !E%L1	 	 	
 # %r0   c                 0   Uc  [         R                  " USSS9nO[        XS5      nX-
  n[         R                  " U5      [         R                  " U R
                  R                  [         R                  " U5      5      -  nU[         R                  " XRS9-   $ )r   r   r   r   r[   )	r(   r   r   signminimumr!   r   absr]   )r,   r@   rB   r   diffterms         r-   rn   HuberLoss.fit_intercept_only  sr      ]]62A6F)&DFwwt}rzz$***:*:BFF4LII

4???r0   )r&   r'   r   )Ng?r   NNr   r   r   s   @r-   r   r     s(    B N LP&*@ @r0   r   c                   :   ^  \ rS rSrSrSU 4S jjrSS jrSrU =r$ )HalfPoissonLossi  aO  Half Poisson deviance loss with log-link, for regression.

Domain:
y_true in non-negative real numbers
y_pred in positive real numbers

Link:
y_pred = exp(raw_prediction)

For a given sample x_i, half the Poisson deviance is defined as::

    loss(x_i) = y_true_i * log(y_true_i/exp(raw_prediction_i))
                - y_true_i + exp(raw_prediction_i)

Half the Poisson deviance is actually the negative log-likelihood up to
constant terms (not involving raw_prediction) and simplifies the
computation of the gradients.
We also skip the constant term `y_true_i * log(y_true_i) - y_true_i`.
c                    > [         TU ]  [        5       [        5       X#S9  [	        S[
        R                  SS5      U l        g )Nr   r   TF)r   r.   r
   r   r   r(   r)   r*   r   s       r-   r.   HalfPoissonLoss.__init__  s:    #%GI" 	 	
  (2664?r0   c                 0    [        X5      U-
  nUb  X2-  nU$ r   r   r,   r@   rB   r   s       r-   rs   (HalfPoissonLoss.constant_to_optimal_zero  s$    V$v-$!Dr0   r*   r   r   	r   r   r   r   r   r.   rs   r   r   r   s   @r-   r   r     s    (@ r0   r   c                   :   ^  \ rS rSrSrSU 4S jjrSS jrSrU =r$ )HalfGammaLossi  a&  Half Gamma deviance loss with log-link, for regression.

Domain:
y_true and y_pred in positive real numbers

Link:
y_pred = exp(raw_prediction)

For a given sample x_i, half Gamma deviance loss is defined as::

    loss(x_i) = log(exp(raw_prediction_i)/y_true_i)
                + y_true/exp(raw_prediction_i) - 1

Half the Gamma deviance is actually proportional to the negative log-
likelihood up to constant terms (not involving raw_prediction) and
simplifies the computation of the gradients.
We also skip the constant term `-log(y_true_i) - 1`.
c                    > [         TU ]  [        5       [        5       X#S9  [	        S[
        R                  SS5      U l        g )Nr   r   F)r   r.   r   r   r   r(   r)   r*   r   s       r-   r.   HalfGammaLoss.__init__&  s3    0wyRW'2665%@r0   c                 H    [         R                  " U5      * S-
  nUb  X2-  nU$ r   )r(   logr   s       r-   rs   &HalfGammaLoss.constant_to_optimal_zero*  s)    v"$!Dr0   r   r   r   r   r   s   @r-   r   r     s    &A r0   r   c                   :   ^  \ rS rSrSrSU 4S jjrSS jrSrU =r$ )HalfTweedieLossi1  a  Half Tweedie deviance loss with log-link, for regression.

Domain:
y_true in real numbers for power <= 0
y_true in non-negative real numbers for 0 < power < 2
y_true in positive real numbers for 2 <= power
y_pred in positive real numbers
power in real numbers

Link:
y_pred = exp(raw_prediction)

For a given sample x_i, half Tweedie deviance loss with p=power is defined
as::

    loss(x_i) = max(y_true_i, 0)**(2-p) / (1-p) / (2-p)
                - y_true_i * exp(raw_prediction_i)**(1-p) / (1-p)
                + exp(raw_prediction_i)**(2-p) / (2-p)

Taking the limits for p=0, 1, 2 gives HalfSquaredError with a log link,
HalfPoissonLoss and HalfGammaLoss.

We also skip constant terms, but those are different for p=0, 1, 2.
Therefore, the loss is not continuous in `power`.

Note furthermore that although no Tweedie distribution exists for
0 < power < 1, it still gives a strictly consistent scoring function for
the expectation.
c                   > [         TU ]  [        [        U5      S9[	        5       UUS9  U R
                  R                  S::  a1  [        [        R                  * [        R                  SS5      U l
        g U R
                  R                  S:  a"  [        S[        R                  SS5      U l
        g [        S[        R                  SS5      U l
        g N)powerr   r   Fr=   T)r   r.   r   r   r   r!   r   r   r(   r)   r*   r,   rB   r   r$   r%   r   s        r-   r.   HalfTweedieLoss.__init__P  s    #%,7	 	 	
 ::q #+RVVGRVVUE#JD ZZ!#+ArvvtU#CD #+Arvvue#DD r0   c                    U R                   R                  S:X  a  [        5       R                  XS9$ U R                   R                  S:X  a  [	        5       R                  XS9$ U R                   R                  S:X  a  [        5       R                  XS9$ U R                   R                  n[        R                  " [        R                  " US5      SU-
  5      SU-
  -  SU-
  -  nUb  XB-  nU$ )Nr   )r@   rB   r>   r=   )r!   r   r   rs   r   r   r(   maximum)r,   r@   rB   pr   s        r-   rs   (HalfTweedieLoss.constant_to_optimal_zero^  s    ::q #%>> ?   ZZ""$== >   ZZ" ?;; <   

  A88BJJvq11q59QUCq1uMD(%Kr0   r   Ng      ?NNr   r   r   s   @r-   r   r   1  s    <E r0   r   c                   0   ^  \ rS rSrSrSU 4S jjrSrU =r$ )HalfTweedieLossIdentityis  a"  Half Tweedie deviance loss with identity link, for regression.

Domain:
y_true in real numbers for power <= 0
y_true in non-negative real numbers for 0 < power < 2
y_true in positive real numbers for 2 <= power
y_pred in positive real numbers for power != 0
y_pred in real numbers for power = 0
power in real numbers

Link:
y_pred = raw_prediction

For a given sample x_i, half Tweedie deviance loss with p=power is defined
as::

    loss(x_i) = max(y_true_i, 0)**(2-p) / (1-p) / (2-p)
                - y_true_i * raw_prediction_i**(1-p) / (1-p)
                + raw_prediction_i**(2-p) / (2-p)

Note that the minimum value of this loss is 0.

Note furthermore that although no Tweedie distribution exists for
0 < power < 1, it still gives a strictly consistent scoring function for
the expectation.
c                 ~  > [         TU ]  [        [        U5      S9[	        5       UUS9  U R
                  R                  S::  a1  [        [        R                  * [        R                  SS5      U l
        O]U R
                  R                  S:  a"  [        S[        R                  SS5      U l
        O![        S[        R                  SS5      U l
        U R
                  R                  S:X  a1  [        [        R                  * [        R                  SS5      U l        g [        S[        R                  SS5      U l        g r   )r   r.   r   r   r   r!   r   r   r(   r)   r*   r+   r   s        r-   r.    HalfTweedieLossIdentity.__init__  s    +%,?	 	 	
 ::q #+RVVGRVVUE#JD ZZ!#+ArvvtU#CD #+Arvvue#DD ::q #+RVVGRVVUE#JD #+Arvvue#DD r0   )r+   r*   r   r   r   s   @r-   r   r   s  s    6E Er0   r   c                   @   ^  \ rS rSrSrSU 4S jjrSS jrS rSrU =r	$ )	HalfBinomialLossi  a	  Half Binomial deviance loss with logit link, for binary classification.

This is also know as binary cross entropy, log-loss and logistic loss.

Domain:
y_true in [0, 1], i.e. regression on the unit interval
y_pred in (0, 1), i.e. boundaries excluded

Link:
y_pred = expit(raw_prediction)

For a given sample x_i, half Binomial deviance is defined as the negative
log-likelihood of the Binomial/Bernoulli distribution and can be expressed
as::

    loss(x_i) = log(1 + exp(raw_pred_i)) - y_true_i * raw_pred_i

See The Elements of Statistical Learning, by Hastie, Tibshirani, Friedman,
section 4.4.1 (about logistic regression).

Note that the formulation works for classification, y = {0, 1}, as well as
logistic regression, y = [0, 1].
If you add `constant_to_optimal_zero` to the loss, you get half the
Bernoulli/binomial deviance.

More details: Inserting the predicted probability y_pred = expit(raw_prediction)
in the loss gives the well known::

    loss(x_i) = - y_true_i * log(y_pred_i) - (1 - y_true_i) * log(1 - y_pred_i)
c                 n   > [         TU ]  [        5       [        5       SUUS9  [	        SSSS5      U l        g Nr=   r!   r"   r#   r$   r%   r   r>   T)r   r.   r   r   r   r*   r   s       r-   r.   HalfBinomialLoss.__init__  s>    $& 	 	
  (1dD9r0   c                 P    [        X5      [        SU-
  SU-
  5      -   nUb  X2-  nU$ r   r   r   s       r-   rs   )HalfBinomialLoss.constant_to_optimal_zero  s3    V$uQZV'DD$!Dr0   c                 4   UR                   S:X  a$  UR                  S   S:X  a  UR                  S5      n[        R                  " UR                  S   S4UR
                  S9nU R                  R                  U5      USS2S4'   SUSS2S4   -
  USS2S4'   U$ zPredict probabilities.

Parameters
----------
raw_prediction : array of shape (n_samples,) or (n_samples, 1)
    Raw prediction values (in link space).

Returns
-------
proba : array of shape (n_samples, 2)
    Element-wise class probabilities.
r=   r>   r   rM   NrF   rG   rH   r(   r|   rN   r"   inverser,   rA   probas      r-   predict_probaHalfBinomialLoss.predict_proba       !#(<(<Q(?1(D+33A6N...q115^=Q=QRii''7ad%1+oadr0   r   r   r   
r   r   r   r   r   r.   rs   r   r   r   r   s   @r-   r   r     s    >: r0   r   c                   \   ^  \ rS rSrSrSrS
U 4S jjrS rSS jrS r	    SS jr
S	rU =r$ )HalfMultinomialLossi  a  Categorical cross-entropy loss, for multiclass classification.

Domain:
y_true in {0, 1, 2, 3, .., n_classes - 1}
y_pred has n_classes elements, each element in (0, 1)

Link:
y_pred = softmax(raw_prediction)

Note: We assume y_true to be already label encoded. The inverse link is
softmax. But the full link function is the symmetric multinomial logit
function.

For a given sample x_i, the categorical cross-entropy loss is defined as
the negative log-likelihood of the multinomial distribution, it
generalizes the binary cross-entropy to more than 2 classes::

    loss_i = log(sum(exp(raw_pred_{i, k}), k=0..n_classes-1))
            - sum(y_true_{i, k} * raw_pred_{i, k}, k=0..n_classes-1)

See [1].

Note that for the hessian, we calculate only the diagonal part in the
classes: If the full hessian for classes k and l and sample i is H_i_k_l,
we calculate H_i_k_k, i.e. k=l.

Parameters
----------
sample_weight : {None, ndarray}
    If sample_weight is None, the hessian might be constant.

n_classes : {None, int}
    The number of classes for classification, else None.

xp : module or None
    Array namespace module. Ignored by the Cython implementation.

device : device or None
    A device object. Ignored by the Cython implementation.

References
----------
.. [1] :arxiv:`Simon, Noah, J. Friedman and T. Hastie.
    "A Blockwise Descent Algorithm for Group-penalized Multiresponse and
    Multinomial Regression".
    <1311.6529>`
Tc                    > [         TU ]  [        5       [        5       UUUS9  [	        S[
        R                  SS5      U l        [	        SSSS5      U l        S U l	        S U l
        S U l        g )Nr   r   TFr>   )r   r.   r	   r   r   r(   r)   r*   r+   class_indexing_offsets
y_true_inty_true_one_hotr,   rB   r#   r$   r%   r   s        r-   r.   HalfMultinomialLoss.__init__  so    ')!# 	 	
  (2664?'1eU; '+#"r0   c                     U R                   R                  U5      =(       a,    [        R                  " UR	                  [
        5      U:H  5      $ r2   )r*   r3   r(   allastypeintr4   s     r-   r6   #HalfMultinomialLoss.in_y_true_range.  s6     ##,,Q/NBFF188C=A;M4NNr0   c                    [         R                  " U R                  UR                  S9n[         R                  " UR                  5      R
                  n[        U R                  5       H<  n[         R                  " X:H  USS9X5'   [         R                  " X5   USU-
  5      X5'   M>     U R                  R                  USSS24   5      R                  S5      $ )a  Compute raw_prediction of an intercept-only model.

This is the softmax of the weighted average of the target, i.e. over
the samples axis=0.

Parameters
----------
y_true : array-like of shape (n_samples,)
    Observed, true target values.

sample_weight : None or array of shape (n_samples,), default=None
    Sample weights.

Returns
-------
raw_prediction : numpy scalar or array of shape (n_classes,)
    Raw predictions of an intercept-only model.
rM   r   ra   r>   N)r(   zerosr#   rN   rd   re   ranger]   rj   r"   reshape)r,   r@   rB   outre   ks         r-   rn   &HalfMultinomialLoss.fit_intercept_only7  s    & hht~~V\\:hhv||$((t~~&AZZ]KCFWWSVS!c'2CF ' yy~~c$'l+33B77r0   c                 8    U R                   R                  U5      $ )zPredict probabilities.

Parameters
----------
raw_prediction : array of shape (n_samples, n_classes)
    Raw prediction values (in link space).

Returns
-------
proba : array of shape (n_samples, n_classes)
    Element-wise class probabilities.
)r"   r   )r,   rA   s     r-   r   !HalfMultinomialLoss.predict_probaQ  s     yy  00r0   c           	      
   UcG  Uc-  [         R                  " U5      n[         R                  " U5      nO0[         R                  " U5      nOUc  [         R                  " U5      nU R                  R                  UUUUUUS9  XE4$ )a  Compute gradient and class probabilities fow raw_prediction.

Parameters
----------
y_true : C-contiguous array of shape (n_samples,)
    Observed, true target values.
raw_prediction : array of shape (n_samples, n_classes)
    Raw prediction values (in link space).
sample_weight : None or C-contiguous array of shape (n_samples,)
    Sample weights.
gradient_out : None or array of shape (n_samples, n_classes)
    A location into which the gradient is stored. If None, a new array
    might be created.
proba_out : None or array of shape (n_samples, n_classes)
    A location into which the class probabilities are stored. If None,
    a new array might be created.
n_threads : int, default=1
    Might use openmp thread parallelism.

Returns
-------
gradient : array of shape (n_samples, n_classes)
    Element-wise gradients.

proba : array of shape (n_samples, n_classes)
    Element-wise class probabilities.
)r@   rA   rB   rO   	proba_outrD   )r(   rE   r!   gradient_proba)r,   r@   rA   rB   rO   r  rD   s          r-   r  "HalfMultinomialLoss.gradient_proba`  s    H  !}}^<MM.9	!}}Y7l3I

!!)'% 	" 	
 &&r0   )r   r+   r*   r   r   N   NNr   r   )r   r   r   r   r   r{   r.   r6   rn   r   r  r   r   r   s   @r-   r   r     s=    .` M#"O841& 5' 5'r0   r   c                   @   ^  \ rS rSrSrSU 4S jjrSS jrS rSrU =r	$ )	ExponentialLossi  a  Exponential loss with (half) logit link, for binary classification.

This is also know as boosting loss.

Domain:
y_true in [0, 1], i.e. regression on the unit interval
y_pred in (0, 1), i.e. boundaries excluded

Link:
y_pred = expit(2 * raw_prediction)

For a given sample x_i, the exponential loss is defined as::

    loss(x_i) = y_true_i * exp(-raw_pred_i)) + (1 - y_true_i) * exp(raw_pred_i)

See:
- J. Friedman, T. Hastie, R. Tibshirani.
  "Additive logistic regression: a statistical view of boosting (With discussion
  and a rejoinder by the authors)." Ann. Statist. 28 (2) 337 - 407, April 2000.
  https://doi.org/10.1214/aos/1016218223
- A. Buja, W. Stuetzle, Y. Shen. (2005).
  "Loss Functions for Binary Class Probability Estimation and Classification:
  Structure and Applications."

Note that the formulation works for classification, y = {0, 1}, as well as
"exponential logistic" regression, y = [0, 1].
Note that this is a proper scoring rule, but without it's canonical link.

More details: Inserting the predicted probability
y_pred = expit(2 * raw_prediction) in the loss gives::

    loss(x_i) = y_true_i * sqrt((1 - y_pred_i) / y_pred_i)
        + (1 - y_true_i) * sqrt(y_pred_i / (1 - y_pred_i))
c                 n   > [         TU ]  [        5       [        5       SUUS9  [	        SSSS5      U l        g r   )r   r.   r   r   r   r*   r   s       r-   r.   ExponentialLoss.__init__  s>    #% 	 	
  (1dD9r0   c                 R    S[         R                  " USU-
  -  5      -  nUb  X2-  nU$ )Nr>   )r(   sqrtr   s       r-   rs   (ExponentialLoss.constant_to_optimal_zero  s1    BGGFa&j122$!Dr0   c                 4   UR                   S:X  a$  UR                  S   S:X  a  UR                  S5      n[        R                  " UR                  S   S4UR
                  S9nU R                  R                  U5      USS2S4'   SUSS2S4   -
  USS2S4'   U$ r   r   r   s      r-   r   ExponentialLoss.predict_proba  r   r0   r   r   r   r   r   s   @r-   r  r    s    !F: r0   r  )
squared_errorabsolute_errorpinball_loss
huber_losspoisson_loss
gamma_losstweedie_lossbinomial_lossmultinomial_lossexponential_lossc                   X    \ rS rSrSr  S	S jr   S
S jr    SS jr   S
S jrSr	g)ArrayAPILossMixini  a  Mixin for loss classes that are compatible with the array API.

Currently this mixin redefines methods:
- __call__(...)
- loss(...)
- loss_gradient(...)
- gradient(...)

such that they work according to the array API specification.
It uses the attributes self.xp and self.device from BaseLoss and it assumes that
methods self._compute_loss and self._compute_gradient are implemented.
Nc                 \    U R                  XSS9n[        [        XSU R                  S95      $ )a   Compute the weighted average loss for the array API losses.

Parameters
----------
y_true : C-contiguous array of shape (n_samples,)
    Observed, true target values.
raw_prediction : C-contiguous array of shape (n_samples,) or array of             shape (n_samples, n_classes)
    Raw prediction values (in link space).
sample_weight : None or C-contiguous array of shape (n_samples,)
    Sample weights.
n_threads : int, default=1
    Ignored by the array API implementation.

Returns
-------
loss : float
    Mean or averaged loss function.
Nr@   rA   rB   )r\   r$   )rI   r   r   r$   )r,   r@   rA   rB   rD   loss_xps         r-   r^   ArrayAPILossMixin.__call__  s4    4 ))  
 XgIJJr0   c                 $    U R                  UUUS9$ )a  Compute the pointwise loss value for each input.

Parameters
----------
y_true : C-contiguous array of shape (n_samples,)
    Observed, true target values.
raw_prediction : C-contiguous array of shape (n_samples,) or array of             shape (n_samples, n_classes)
    Raw prediction values (in link space).
sample_weight : None or C-contiguous array of shape (n_samples,)
    Sample weights.
loss_out : None or C-contiguous array of shape (n_samples,)
    Ignored by the array API implementation.
n_threads : int, default=1
    Ignored by the array API implementation.

Returns
-------
loss : array of shape (n_samples,)
    Element-wise loss function.
r+  )_compute_lossrJ   s         r-   rI   ArrayAPILossMixin.loss  s%    : !!)' " 
 	
r0   c                 L    U R                  UUUS9nU R                  UUUS9nXx4$ )a  Compute loss and gradient w.r.t. raw_prediction for each input.

Parameters
----------
y_true : C-contiguous array of shape (n_samples,)
    Observed, true target values.
raw_prediction : C-contiguous array of shape (n_samples,) or array of             shape (n_samples, n_classes)
    Raw prediction values (in link space).
sample_weight : None or C-contiguous array of shape (n_samples,)
    Sample weights.
loss_out : None or C-contiguous array of shape (n_samples,)
    Ignored by the array API implementation.
gradient_out : None or C-contiguous array of shape (n_samples,) or array             of shape (n_samples, n_classes)
    Ignored by the array API implementation.
n_threads : int, default=1
    Ignored by the array API implementation.

Returns
-------
loss : array of shape (n_samples,)
    Element-wise loss function.

gradient : array of shape (n_samples,) or (n_samples, n_classes)
    Element-wise gradients.
r+  )r/  _compute_gradient)	r,   r@   rA   rB   rC   rO   rD   rI   rS   s	            r-   rP   ArrayAPILossMixin.loss_gradientA  sM    H !!)' " 

 )))' * 

 ~r0   c                 $    U R                  UUUS9$ )a  Compute gradient of loss w.r.t raw_prediction for each input.

Parameters
----------
y_true : C-contiguous array of shape (n_samples,)
    Observed, true target values.
raw_prediction : C-contiguous array of shape (n_samples,) or array of             shape (n_samples, n_classes)
    Raw prediction values (in link space).
sample_weight : None or C-contiguous array of shape (n_samples,)
    Sample weights.
gradient_out : None or C-contiguous array of shape (n_samples,) or array             of shape (n_samples, n_classes)
    Ignored by the array API implementation.
n_threads : int, default=1
    Ignored by the array API implementation.

Returns
-------
gradient : array of shape (n_samples,) or (n_samples, n_classes)
    Element-wise gradients.
r+  )r2  rT   s         r-   rS   ArrayAPILossMixin.gradientq  s%    < %%)' & 
 	
r0   r   r   r   r   )
r   r   r   r   r   r^   rI   rP   rS   r   r   r0   r-   r)  r)    sK    " KF !
N .h "
r0   r)  c                 H   U R                   UR                  :X  a  / SQO/ SQnUR                  XS   :*  UUR                  XS   :*  UR                  U5      UR                  XS   :*  UR	                  SU-   5      UR                  XS   :*  U SU-  -   U 5      5      5      5      $ )a6  Numerically stable version of log(1 + exp(x)) that is compatible with
the array API.

Parameters
----------
raw_prediction : C-contiguous array of shape (n_samples,) or array of         shape (n_samples, n_classes)
    Raw prediction values (in link space).
raw_prediction_exp : C-contiguous array of shape (n_samples,) or array of         shape (n_samples, n_classes)
    Exponential of the raw prediction values.
xp : module, default=None
    Array namespace module.

Returns
-------
log1pexp : float
    Numerically stable value for log(1 + exp(raw_prediction)).
)r     gfffff@@)r  	   g333333-@r   r>   r=   g      ?r  )rN   ry   wherelog1pr   )rA   raw_prediction_expr$   	constantss       r-   	_log1pexpr?    s    j 2::- 	 
 88A,&
l*HH'(HHA,.s//0"l2"Q);%;;"	
 r0   c                   F    \ rS rSrSr    SS jr  S	S jr  S	S jrSrg)
HalfBinomialLossArrayAPIi  zHA version of the HalfBinomialLoss that is compatible with the array API.Nc                     U R                   R                  U5      nU R                  UUUUS9nU R                  UUUUS9n	X4$ N)r@   rA   rB   r=  r$   expr/  r2  
r,   r@   rA   rB   rC   rO   rD   r=  rI   rS   s
             r-   rP   &HalfBinomialLossArrayAPI.loss_gradient  e     "WW[[8!!)'1	 " 
 )))'1	 * 
 ~r0   c                     Uc  U R                   R                  U5      n[        UUU R                   S9nXQU-  -
  nUb  Xc-  nU$ )N)rA   r=  r$   )r$   rE  r?  )r,   r@   rA   rB   r=  log1pexprI   s          r-   r/  &HalfBinomialLossArrayAPI._compute_loss  sV     %!%^!<)1ww

 >11$!Dr0   c                     U R                   nUc  UR                  U5      nSU-  nUR                  X"R                  UR                  :X  a  SOS:  SU-
  X-  -
  SU-   -  XA-
  5      nUb  Xs-  nU$ )Nr>   r7  r9  )r$   rE  r;  rN   ry   )r,   r@   rA   rB   r=  r$   neg_raw_prediction_expgrads           r-   r2  *HalfBinomialLossArrayAPI._compute_gradient  s     WW%!#!7!"%7!7xx%9%9RZZ%GcSQ&jF;;))+'	
 $!Dr0   r   r   NN	r   r   r   r   r   rP   r/  r2  r   r   r0   r-   rA  rA    s2    R 8 . r0   rA  c                   H   ^  \ rS rSrSrSU 4S jjr SS jr SS jrSrU =r	$ )	HalfMultinomialLossArrayAPIi%  aq  A version of the HalfMultinomialLoss that is compatible with the array API.

Parameters
----------
sample_weight : {None, ndarray}
    If sample_weight is None, the hessian might be constant.

n_classes : {None, int}
    The number of classes for classification, else None.

xp : module or None
    Array namespace module.

device : device or None
    A device object.
c                 L   > [         TU ]  X#US9  S U l        S U l        S U l        g )N)r#   r$   r%   )r   r.   r   r   r   r   s        r-   r.   $HalfMultinomialLossArrayAPI.__init__7  s0    9FC '+# #r0   c                    U R                   nU R                  n[        USUS9nU R                  c  UR	                  XR
                  US9U l        U R                  c/  UR                  UR                  S   US9U R                  -  U l        UR                  [        U5      U R                  U R                  -   5      nXg-
  nUb  X-  nU$ )Nr>   )rb   r$   rN   r%   r   )r%   )r$   r%   r   r   asarrayint64r   arangerG   r#   taker   )	r,   r@   rA   rB   r$   r%   log_sum_exptrue_label_probsrI   s	            r-   r/  )HalfMultinomialLossArrayAPI._compute_lossD  s     WW aB???" jjxxjODO&&.		&,,q/&	9DNNJ ' 77>"DOOd6Q6Q$Q
 -$!Dr0   c                 R   U R                   nU R                  nU R                  cZ  U R                  c  UR	                  XR
                  US9U l        [        U R                  U R                  UR                  S9U l        [        U5      nX`R                  -  nUb  XcS S 2S 4   -  nU$ )NrW  )num_classesrN   )
r$   r%   r   r   rX  rY  r   r#   rN   r   )r,   r@   rA   rB   r$   device_rN  s          r-   r2  -HalfMultinomialLossArrayAPI._compute_gradient\  s     WW++&&"$**V88G*"T") NN$**#D
 ~& 	###$!T'**Dr0   )r   r   r   r  r   )
r   r   r   r   r   r.   r/  r2  r   r   r   s   @r-   rS  rS  %  s&    "#" 	8 	 r0   rS  c                   F    \ rS rSrSr    SS jr  S	S jr  S	S jrSrg)
HalfPoissonLossArrayAPIi}  zGA version of the HalfPoissonLoss that is compatible with the array API.Nc                     U R                   R                  U5      nU R                  UUUUS9nU R                  UUUUS9n	X4$ rC  rD  rF  s
             r-   rP   %HalfPoissonLossArrayAPI.loss_gradient  rH  r0   c                 ^    Uc  U R                   R                  U5      nXAU-  -
  nUb  XS-  nU$ r   r$   rE  )r,   r@   rA   rB   r=  rI   s         r-   r/  %HalfPoissonLossArrayAPI._compute_loss  s=     %!%^!<!^$;;$!Dr0   c                 X    Uc  U R                   R                  U5      nXA-
  nUb  XS-  nU$ r   rh  )r,   r@   rA   rB   r=  rN  s         r-   r2  )HalfPoissonLossArrayAPI._compute_gradient  s8     %!%^!<!*$!Dr0   r   r   rP  rQ  r   r0   r-   rd  rd  }  s2    Q 8 $ r0   rd  )7r   r   numpyr(   scipy.specialr   sklearn._loss._lossr   r   r   r   r	   r
   r   r   r   r   r   sklearn._loss.linkr   r   r   r   r   r   !sklearn.externals.array_api_extrar   sklearn.utilsr   sklearn.utils._array_apir   r   r   sklearn.utils.extmathr   sklearn.utils.statsr   r   r   r   r   r   r   r   r   r   r   r   r  _LOSSESr)  r?  rA  rS  rd  r   r0   r-   <module>rv     se  *        6 & 
 * 4*T! T!n6x 62$CH $CN=( =@I@ I@Xh DH >?h ?D-Eh -E`Dx DNk'( k'\Hh HX &###%+'b
 b
JHVA02B AHU"35H Up5/ 5r0   