
    sg&                         d dl Z d dlZd dlmZ d dlmZ d dlmZmZ d dl	m
Z
mZ d dlmZ dgZd Zd	 Zd
 Z G d de      Zy)    N)constraints)Distribution)_batch_mahalanobis	_batch_mv)_standard_normallazy_property)_sizeLowRankMultivariateNormalc                 :   | j                  d      }| j                  |j                  d      z  }t        j                  ||       j                         }|j                  d||z        dddd|dz   fxx   dz  cc<   t        j                  j                  |      S )z
    Computes Cholesky of :math:`I + W.T @ inv(D) @ W` for a batch of matrices :math:`W`
    and a batch of vectors :math:`D`.
    N   )	sizemT	unsqueezetorchmatmul
contiguousviewlinalgcholesky)WDmWt_DinvKs        b/var/www/html/venv/lib/python3.12/site-packages/torch/distributions/lowrank_multivariate_normal.py_batch_capacitance_trilr      s    
 	
r
AddQ[[_$GWa ++-AFF2q1uaAEk"a'"<<  ##    c                     d|j                  dd      j                         j                  d      z  |j                         j                  d      z   S )z
    Uses "matrix determinant lemma"::
        log|W @ W.T + D| = log|C| + log|D|,
    where :math:`C` is the capacitance matrix :math:`I + W.T @ inv(D) @ W`, to compute
    the log determinant.
       r   r   )dim1dim2)diagonallogsum)r   r   capacitance_trils      r   _batch_lowrank_logdetr(      sP     ((br(:>>@DDRHH1557;;
L  r   c                     | j                   |j                  d      z  }t        ||      }|j                  d      |z  j	                  d      }t        ||      }||z
  S )a  
    Uses "Woodbury matrix identity"::
        inv(W @ W.T + D) = inv(D) - inv(D) @ W @ inv(C) @ W.T @ inv(D),
    where :math:`C` is the capacitance matrix :math:`I + W.T @ inv(D) @ W`, to compute the squared
    Mahalanobis distance :math:`x.T @ inv(W @ W.T + D) @ x`.
    r   r!   r   )r   r   r   powr&   r   )r   r   xr'   r   	Wt_Dinv_xmahalanobis_term1mahalanobis_term2s           r   _batch_lowrank_mahalanobisr/   '   s]     ddQ[[_$G'1%IqA**2.*+;YG000r   c                       e Zd ZdZej
                   ej                  ej                  d       ej                  ej                  d      dZ	ej
                  Z
dZd fd	Zd fd	Zed        Zed	        Zed
        Zed        Zed        Zed        Z ej.                         fdedej2                  fdZd Zd Z xZS )r
   a  
    Creates a multivariate normal distribution with covariance matrix having a low-rank form
    parameterized by :attr:`cov_factor` and :attr:`cov_diag`::

        covariance_matrix = cov_factor @ cov_factor.T + cov_diag

    Example:
        >>> # xdoctest: +REQUIRES(env:TORCH_DOCTEST_LAPACK)
        >>> # xdoctest: +IGNORE_WANT("non-deterministic")
        >>> m = LowRankMultivariateNormal(torch.zeros(2), torch.tensor([[1.], [0.]]), torch.ones(2))
        >>> m.sample()  # normally distributed with mean=`[0,0]`, cov_factor=`[[1],[0]]`, cov_diag=`[1,1]`
        tensor([-0.2102, -0.5429])

    Args:
        loc (Tensor): mean of the distribution with shape `batch_shape + event_shape`
        cov_factor (Tensor): factor part of low-rank form of covariance matrix with shape
            `batch_shape + event_shape + (rank,)`
        cov_diag (Tensor): diagonal part of low-rank form of covariance matrix with shape
            `batch_shape + event_shape`

    Note:
        The computation for determinant and inverse of covariance matrix is avoided when
        `cov_factor.shape[1] << cov_factor.shape[0]` thanks to `Woodbury matrix identity
        <https://en.wikipedia.org/wiki/Woodbury_matrix_identity>`_ and
        `matrix determinant lemma <https://en.wikipedia.org/wiki/Matrix_determinant_lemma>`_.
        Thanks to these formulas, we just need to compute the determinant and inverse of
        the small size "capacitance" matrix::

            capacitance = I + cov_factor.T @ inv(cov_diag) @ cov_factor
    r!   r   )loc
cov_factorcov_diagTc           	         |j                         dk  rt        d      |j                  dd  }|j                         dk  rt        d      |j                  dd |k7  rt        d|d    d	      |j                  dd  |k7  rt        d
|       |j                  d      }|j                  d      }	 t	        j
                  |||      \  }| _        }|d   | _        |d   | _	        | j                  j                  d d }	|| _
        || _        t        ||      | _        t        
| =  |	||       y # t        $ r8}t        d|j                   d|j                   d|j                         |d }~ww xY w)Nr   z%loc must be at least one-dimensional.r   r!   zScov_factor must be at least two-dimensional, with optional leading batch dimensionsr   z2cov_factor must be a batch of matrices with shape r   z x mz/cov_diag must be a batch of vectors with shape zIncompatible batch shapes: loc z, cov_factor z, cov_diag ).r   validate_args)dim
ValueErrorshaper   r   broadcast_tensorsr2   RuntimeErrorr1   r3   _unbroadcasted_cov_factor_unbroadcasted_cov_diagr   _capacitance_trilsuper__init__)selfr1   r2   r3   r6   event_shapeloc_	cov_diag_ebatch_shape	__class__s             r   r@   z"LowRankMultivariateNormal.__init__\   s   779q=DEEiin>>a9  Br"k1D[QR^DTTXY  >>"#+-A+O  }}R &&r*		/4/F/Fj)0,D$/9 <!&)hhnnSb))3&'/$!8X!NkO  	1#))M*JZJZI[[fgogugufvw	s   4 D3 3	E4<3E//E4c                 8   | j                  t        |      }t        j                  |      }|| j                  z   }| j
                  j                  |      |_        | j                  j                  |      |_        | j                  j                  || j                  j                  dd  z         |_        | j                  |_
        | j                  |_        | j                  |_        t        t        |;  || j                  d       | j                  |_        |S )Nr   Fr5   )_get_checked_instancer
   r   SizerB   r1   expandr3   r2   r9   r<   r=   r>   r?   r@   _validate_args)rA   rF   	_instancenew	loc_shaperG   s        r   rK   z LowRankMultivariateNormal.expand   s    (()BINjj-$"2"22	((//),}}++I6//	DOO<Q<QRTRU<V0VW(,(F(F%&*&B&B# $ 6 6'6)) 	7 	
 "00
r   c                     | j                   S Nr1   rA   s    r   meanzLowRankMultivariateNormal.mean       xxr   c                     | j                   S rQ   rR   rS   s    r   modezLowRankMultivariateNormal.mode   rU   r   c                     | j                   j                  d      j                  d      | j                  z   j	                  | j
                  | j                  z         S )Nr!   r   )r<   r*   r&   r=   rK   _batch_shape_event_shaperS   s    r   variancez"LowRankMultivariateNormal.variance   sN     **..q155b9D<X<XX
&""T%6%66
7	8r   c                    | j                   d   }| j                  j                         j                  d      }| j                  |z  }t        j                  ||j                        j                         }|j                  d||z        d d d d |dz   fxx   dz  cc<   |t
        j                  j                  |      z  }|j                  | j                  | j                   z   | j                   z         S )Nr   r   r   )rZ   r=   sqrtr   r<   r   r   r   r   r   r   r   rK   rY   )rA   ncov_diag_sqrt_unsqueeze
Dinvsqrt_Wr   
scale_trils         r   ra   z$LowRankMultivariateNormal.scale_tril   s     a "&">">"C"C"E"O"OPR"S336MM
LLZ]]3>>@	r1q5!XAX+&!+&,u||/D/DQ/GG
   1 11D4E4EE
 	
r   c                    t        j                  | j                  | j                  j                        t        j                  | j
                        z   }|j                  | j                  | j                  z   | j                  z         S rQ   )	r   r   r<   r   
diag_embedr=   rK   rY   rZ   )rA   covariance_matrixs     r   rd   z+LowRankMultivariateNormal.covariance_matrix   su    !LL**D,J,J,M,M
T99:; !'' 1 11D4E4EE
 	
r   c                    | j                   j                  | j                  j                  d      z  }t        j
                  j                  | j                  |d      }t	        j                  | j                  j                               |j                  |z  z
  }|j                  | j                  | j                  z   | j                  z         S )Nr   F)upper)r<   r   r=   r   r   r   solve_triangularr>   rc   
reciprocalrK   rY   rZ   )rA   r   Aprecision_matrixs       r   rj   z*LowRankMultivariateNormal.precision_matrix   s     **--**44R89 	 LL))$*@*@'QV)WT99DDFG!$$QR(R 	  && 1 11D4E4EE
 	
r   sample_shapereturnc                    | j                  |      }|d d | j                  j                  dd  z   }t        || j                  j
                  | j                  j                        }t        || j                  j
                  | j                  j                        }| j                  t        | j                  |      z   | j                  j                         |z  z   S )Nr   )dtypedevice)_extended_shaper2   r9   r   r1   rn   ro   r   r<   r=   r]   )rA   rk   r9   W_shapeeps_Weps_Ds         r   rsamplez!LowRankMultivariateNormal.rsample   s    $$\2*t44RS99 txxW dhhnnTXX__UHH66>?**//1E9:	
r   c                    | j                   r| j                  |       || j                  z
  }t        | j                  | j
                  || j                        }t        | j                  | j
                  | j                        }d| j                  d   t        j                  dt        j                  z        z  |z   |z   z  S )Ng      r   r!   )rL   _validate_sampler1   r/   r<   r=   r>   r(   rZ   mathr%   pi)rA   valuediffMlog_dets        r   log_probz"LowRankMultivariateNormal.log_prob   s    !!%(txx&**((""	
 (**((""

 t((+dhhq477{.CCgMPQQRRr   c                 @   t        | j                  | j                  | j                        }d| j                  d   dt        j                  dt
        j                  z        z   z  |z   z  }t        | j                        dk(  r|S |j                  | j                        S )Ng      ?r   g      ?r!   )r(   r<   r=   r>   rZ   rw   r%   rx   lenrY   rK   )rA   r|   Hs      r   entropyz!LowRankMultivariateNormal.entropy   s    '**((""

 4$$Q'3!dgg+1F+FG'QRt  !Q&H88D--..r   rQ   )__name__
__module____qualname____doc__r   real_vectorindependentrealpositivearg_constraintssupporthas_rsampler@   rK   propertyrT   rW   r   r[   ra   rd   rj   r   rJ   r	   Tensorrt   r}   r   __classcell__)rG   s   @r   r
   r
   5   s   > &&-k--k.>.>B+K++K,@,@!DO
 %%GK#PJ      8 8
 
 
  
 
 
 
  -7EJJL 	
E 	
U\\ 	
S"
/r   )rw   r   torch.distributionsr    torch.distributions.distributionr   'torch.distributions.multivariate_normalr   r   torch.distributions.utilsr   r   torch.typesr	   __all__r   r(   r/   r
    r   r   <module>r      sA      + 9 Q E  '
'	$	1{/ {/r   