Ë
    P/æjÍV  ã                   óº  — d dl Z d dlmZmZ d dlZd dlmZ d dlmZ g Z		 	 	 	 ddej
                  dej
                  dej
                  de
d	ed
ededej
                  fd„Z G d„ dej                  j                  «      Z G d„ dej                  j                  «      Z G d„ dej                  j                  «      Z G d„ dej                  j                  «      Zy)é    N)ÚOptionalÚUnion)ÚTensor)Ú
functionalÚpsd_sÚpsd_nÚreference_vectorÚsolutionÚdiagonal_loadingÚdiag_epsÚepsÚreturnc                 óæ   — |dk(  rt        j                  | |||||«      }|S |dk(  rt        j                  | «      }nt        j                  | ||||¬«      }t        j                  ||||||«      }|S )a¼  Compute the MVDR beamforming weights with ``solution`` argument.

    Args:
        psd_s (torch.Tensor): The complex-valued power spectral density (PSD) matrix of target speech.
            Tensor with dimensions `(..., freq, channel, channel)`.
        psd_n (torch.Tensor): The complex-valued power spectral density (PSD) matrix of noise.
            Tensor with dimensions `(..., freq, channel, channel)`.
        reference_vector (torch.Tensor): one-hot reference channel matrix.
        solution (str, optional): Solution to compute the MVDR beamforming weights.
            Options: [``ref_channel``, ``stv_evd``, ``stv_power``]. (Default: ``ref_channel``)
        diagonal_loading (bool, optional): If ``True``, enables applying diagonal loading to ``psd_n``.
            (Default: ``True``)
        diag_eps (float, optional): The coefficient multiplied to the identity matrix for diagonal loading.
            It is only effective when ``diagonal_loading`` is set to ``True``. (Default: ``1e-7``)
        eps (float, optional): Value to add to the denominator in the beamforming weight formula.
            (Default: ``1e-8``)

    Returns:
        torch.Tensor: the mvdr beamforming weight matrix
    Úref_channelÚstv_evd)r   r   )ÚFÚmvdr_weights_soudenÚrtf_evdÚ	rtf_powerÚmvdr_weights_rtf)	r   r   r	   r
   r   r   r   Úbeamform_vectorÚstvs	            úg/root/repos/pocs/video-evals/.venv/lib/python3.12/site-packages/torchaudio/transforms/_multi_channel.pyÚ_get_mvdr_vectorr      s‡   € ð: �=Ò Ü×/Ñ/°°uÐ>NÐP`ÐbjÐloÓpˆð Ðð �yÒ Ü—)‘)˜EÓ"‰Cä—+‘+˜e UÐ,<ÐO_ÐjrÔsˆCÜ×,Ñ,¨S°%Ð9IÐK[Ð]eÐgjÓkˆàÐó    c                   ór   ‡ — e Zd ZdZd	dededefˆ fd„Zd
dej                  de	ej                     fd„Z
ˆ xZS )ÚPSDaä  Compute cross-channel power spectral density (PSD) matrix.

    .. devices:: CPU CUDA

    .. properties:: Autograd TorchScript

    Args:
        multi_mask (bool, optional): If ``True``, only accepts multi-channel Time-Frequency masks. (Default: ``False``)
        normalize (bool, optional): If ``True``, normalize the mask along the time dimension. (Default: ``True``)
        eps (float, optional): Value to add to the denominator in mask normalization. (Default: ``1e-15``)
    Ú
multi_maskÚ	normalizer   c                 óL   •— t         ‰| �  «        || _        || _        || _        y ©N)ÚsuperÚ__init__r   r   r   )Úselfr   r   r   Ú	__class__s       €r   r#   zPSD.__init__D   s#   ø€ Ü‰ÑÔØ$ˆŒØ"ˆŒØˆ�r   ÚspecgramÚmaskc                 óž   — |�| j                   r|j                  d¬«      }t        j                  ||| j                  | j
                  «      }|S )a  
        Args:
            specgram (torch.Tensor): Multi-channel complex-valued spectrum.
                Tensor with dimensions `(..., channel, freq, time)`.
            mask (torch.Tensor or None, optional): Time-Frequency mask for normalization.
                Tensor with dimensions `(..., freq, time)` if multi_mask is ``False`` or
                with dimensions `(..., channel, freq, time)` if multi_mask is ``True``.
                (Default: ``None``)

        Returns:
            torch.Tensor: The complex-valued PSD matrix of the input spectrum.
                Tensor with dimensions `(..., freq, channel, channel)`
        éýÿÿÿ©Údim)r   Úmeanr   Úpsdr   r   )r$   r&   r'   r-   s       r   ÚforwardzPSD.forwardJ   sB   € ð ÐØ�Šà—y‘y R�yÓ(�Ü�e‰e�H˜d D§N¡N°D·H±HÓ=ˆàˆ
r   )FTgVçž¯Ò<r!   )Ú__name__Ú
__module__Ú__qualname__Ú__doc__ÚboolÚfloatr#   Útorchr   r   r.   Ú__classcell__©r%   s   @r   r   r   7   sB   ø„ ñ
ñ 4ð ¸Dð Èeõ ñ §¡ð °H¸U¿\¹\Ñ4J÷ r   r   c                   ó  ‡ — e Zd ZdZ	 	 	 	 	 	 ddedededededefˆ fd„Z	 	 	 	 dd	e	j                  d
e	j                  de	j                  de	j                  de	j                  dedededede	j                  fd„Zd	e	j                  de	j                  de	j                  fd„Zd
e	j                  de	j                  de	j                  fd„Z	 dde	j                  de	j                  dee	j                     de	j                  fd„Zˆ xZS )ÚMVDRaÈ  Minimum Variance Distortionless Response (MVDR) module that performs MVDR beamforming with Time-Frequency masks.

    .. devices:: CPU CUDA

    .. properties:: Autograd TorchScript

    Based on https://github.com/espnet/espnet/blob/master/espnet2/enh/layers/beamformer.py

    We provide three solutions of MVDR beamforming. One is based on *reference channel selection*
    :cite:`souden2009optimal` (``solution=ref_channel``).

    .. math::
        \textbf{w}_{\text{MVDR}}(f) =        \frac{{{\bf{\Phi}_{\textbf{NN}}^{-1}}(f){\bf{\Phi}_{\textbf{SS}}}}(f)}        {\text{Trace}({{{\bf{\Phi}_{\textbf{NN}}^{-1}}(f) \bf{\Phi}_{\textbf{SS}}}(f))}}\bm{u}

    where :math:`\bf{\Phi}_{\textbf{SS}}` and :math:`\bf{\Phi}_{\textbf{NN}}` are the covariance        matrices of speech and noise, respectively. :math:`\bf{u}` is an one-hot vector to determine the         reference channel.

    The other two solutions are based on the steering vector (``solution=stv_evd`` or ``solution=stv_power``).

    .. math::
        \textbf{w}_{\text{MVDR}}(f) =        \frac{{{\bf{\Phi}_{\textbf{NN}}^{-1}}(f){\bm{v}}(f)}}        {{\bm{v}^{\mathsf{H}}}(f){\bf{\Phi}_{\textbf{NN}}^{-1}}(f){\bm{v}}(f)}

    where :math:`\bm{v}` is the acoustic transfer function or the steering vector.        :math:`.^{\mathsf{H}}` denotes the Hermitian Conjugate operation.

    We apply either *eigenvalue decomposition*
    :cite:`higuchi2016robust` or the *power method* :cite:`mises1929praktische` to get the
    steering vector from the PSD matrix of speech.

    After estimating the beamforming weight, the enhanced Short-time Fourier Transform (STFT) is obtained by

    .. math::
        \hat{\bf{S}} = {\bf{w}^\mathsf{H}}{\bf{Y}}, {\bf{w}} \in \mathbb{C}^{M \times F}

    where :math:`\bf{Y}` and :math:`\hat{\bf{S}}` are the STFT of the multi-channel noisy speech and        the single-channel enhanced speech, respectively.

    For online streaming audio, we provide a *recursive method* :cite:`higuchi2017online` to update the
    PSD matrices of speech and noise, respectively.

    Args:
        ref_channel (int, optional): Reference channel for beamforming. (Default: ``0``)
        solution (str, optional): Solution to compute the MVDR beamforming weights.
            Options: [``ref_channel``, ``stv_evd``, ``stv_power``]. (Default: ``ref_channel``)
        multi_mask (bool, optional): If ``True``, only accepts multi-channel Time-Frequency masks. (Default: ``False``)
        diagonal_loading (bool, optional): If ``True``, enables applying diagonal loading to the covariance matrix
            of the noise. (Default: ``True``)
        diag_eps (float, optional): The coefficient multiplied to the identity matrix for diagonal loading.
            It is only effective when ``diagonal_loading`` is set to ``True``. (Default: ``1e-7``)
        online (bool, optional): If ``True``, updates the MVDR beamforming weights based on
            the previous covarience matrices. (Default: ``False``)

    Note:
        To improve the numerical stability, the input spectrogram will be converted to double precision
        (``torch.complex128`` or ``torch.cdouble``) dtype for internal computation. The output spectrogram
        is converted to the dtype of the input spectrogram to be compatible with other modules.

    Note:
        If you use ``stv_evd`` solution, the gradient of the same input may not be identical if the
        eigenvalues of the PSD matrix are not distinct (i.e. some eigenvalues are close or identical).
    r   r
   r   Údiag_loadingr   Úonlinec                 ó
  •— t         ‰| �  «        |dvrt        dj                  |«      «      ‚|| _        || _        || _        || _        || _        || _	        t        |«      | _        t        j                  d«      }t        j                  d«      }t        j                  d«      }	t        j                  d«      }
| j                  d|«       | j                  d|«       | j                  d|	«       | j                  d|
«       y )N)r   r   Ú	stv_powerzK`solution` must be one of ["ref_channel", "stv_evd", "stv_power"]. Given {}é   r   r   Ú
mask_sum_sÚ
mask_sum_n)r"   r#   Ú
ValueErrorÚformatr   r
   r   r:   r   r;   r   r-   r5   ÚzerosÚregister_buffer)r$   r   r
   r   r:   r   r;   r   r   r?   r@   r%   s              €r   r#   zMVDR.__init__¥   sè   ø€ ô 	‰ÑÔØð 
ñ 
ô
 Ø]×dÑdÐemÓnóð ð 'ˆÔØ ˆŒØ$ˆŒØ(ˆÔØ ˆŒØˆŒÜ�z“?ˆŒä#Ÿk™k¨!›nˆÜ#Ÿk™k¨!›nˆÜ#(§;¡;¨q£>ˆ
Ü#(§;¡;¨q£>ˆ
Ø×Ñ˜W eÔ,Ø×Ñ˜W eÔ,Ø×Ñ˜\¨:Ô6Ø×Ñ˜\¨:Õ6r   r   r   Úmask_sÚmask_nr	   r   r   r   c
           	      óD  — | j                   r$|j                  d¬«      }|j                  d¬«      }| j                  j                  dk(  rM|| _        || _        |j                  d¬«      | _        |j                  d¬«      | _        t        |||||||	«      S | j                  ||«      }| j                  ||«      }|| _        || _        | j                  |j                  d¬«      z   | _        | j                  |j                  d¬«      z   | _        t        |||||||	«      S )aö  Recursively update the MVDR beamforming vector.

        Args:
            psd_s (torch.Tensor): The complex-valued power spectral density (PSD) matrix of target speech.
                Tensor with dimensions `(..., freq, channel, channel)`.
            psd_n (torch.Tensor): The complex-valued power spectral density (PSD) matrix of noise.
                Tensor with dimensions `(..., freq, channel, channel)`.
            mask_s (torch.Tensor): Time-Frequency mask of the target speech.
                Tensor with dimensions `(..., freq, time)` if multi_mask is ``False``
                or with dimensions `(..., channel, freq, time)` if multi_mask is ``True``.
            mask_n (torch.Tensor or None, optional): Time-Frequency mask of the noise.
                Tensor with dimensions `(..., freq, time)` if multi_mask is ``False``
                or with dimensions `(..., channel, freq, time)` if multi_mask is ``True``.
            reference_vector (torch.Tensor): One-hot reference channel matrix.
            solution (str, optional): Solution to compute the MVDR beamforming weights.
                Options: [``ref_channel``, ``stv_evd``, ``stv_power``]. (Default: ``ref_channel``)
            diagonal_loading (bool, optional): If ``True``, enables applying diagonal loading to ``psd_n``.
                (Default: ``True``)
            diag_eps (float, optional): The coefficient multiplied to the identity matrix for diagonal loading.
                It is only effective when ``diagonal_loading`` is set to ``True``. (Default: ``1e-7``)
            eps (float, optional): Value to add to the denominator in the beamforming weight formula.
                (Default: ``1e-8``)

        Returns:
            torch.Tensor: The MVDR beamforming weight matrix.
        r)   r*   r>   éÿÿÿÿ)r   r,   r   Úndimr   Úsumr?   r@   r   Ú_get_updated_psd_speechÚ_get_updated_psd_noise)
r$   r   r   rE   rF   r	   r
   r   r   r   s
             r   Ú_get_updated_mvdr_vectorzMVDR._get_updated_mvdr_vectorÈ   s  € ðL �?Š?à—[‘[ R�[Ó(ˆFØ—[‘[ R�[Ó(ˆFØ�:‰:�?‰?˜aÒØˆDŒJØˆDŒJØ$Ÿj™j¨R˜jÓ0ˆDŒOØ$Ÿj™j¨R˜jÓ0ˆDŒOÜ# E¨5Ð2BÀHÐN^Ð`hÐjmÓnÐnà×0Ñ0°¸Ó?ˆEØ×/Ñ/°°vÓ>ˆEØˆDŒJØˆDŒJØ"Ÿo™o°·
±
¸r°
Ó0BÑBˆDŒOØ"Ÿo™o°·
±
¸r°
Ó0BÑBˆDŒOÜ# E¨5Ð2BÀHÐN^Ð`hÐjmÓnÐnr   c                 óØ   — | j                   | j                   |j                  d¬«      z   z  }d| j                   |j                  d¬«      z   z  }| j                  |d   z  ||d   z  z   }|S )aÊ  Update psd of speech recursively.

        Args:
            psd_s (torch.Tensor): The complex-valued power spectral density (PSD) matrix of target speech.
                Tensor with dimensions `(..., freq, channel, channel)`.
            mask_s (torch.Tensor): Time-Frequency mask of the target speech.
                Tensor with dimensions `(..., freq, time)`.

        Returns:
            torch.Tensor: The updated PSD matrix of target speech.
        rH   r*   r>   ©.NN)r?   rJ   r   )r$   r   rE   Ú	numeratorÚdenominators        r   rK   zMVDR._get_updated_psd_speech  ók   € ð —O‘O t§¡¸¿¹È¸Ó9KÑ'KÑLˆ	Ø˜4Ÿ?™?¨V¯Z©Z¸B¨ZÓ-?Ñ?Ñ@ˆØ—
‘
˜Y Ñ7Ñ7¸%À+ÈoÑB^Ñ:^Ñ^ˆØˆr   c                 óØ   — | j                   | j                   |j                  d¬«      z   z  }d| j                   |j                  d¬«      z   z  }| j                  |d   z  ||d   z  z   }|S )aÄ  Update psd of noise recursively.

        Args:
            psd_n (torch.Tensor): The complex-valued power spectral density (PSD) matrix of noise.
                Tensor with dimensions `(..., freq, channel, channel)`.
            mask_n (torch.Tensor or None, optional): Time-Frequency mask of the noise.
                Tensor with dimensions `(..., freq, time)`.

        Returns:
            torch.Tensor:  The updated PSD matrix of noise.
        rH   r*   r>   rO   )r@   rJ   r   )r$   r   rF   rP   rQ   s        r   rL   zMVDR._get_updated_psd_noise  rR   r   r&   c           
      ó„  — |j                   }|j                  dk  rt        d|j                  › �«      ‚|j	                  «       st        d|j                   › �«      ‚|j                   t
        j                  k(  r|j                  «       }|€t        j                  d«       d|z
  }| j                  ||«      }| j                  ||«      }t        j                  |j                  «       dd |j                  t
        j                  ¬«      }|d	| j                  f   j                  d«       | j                   r7| j#                  |||||| j$                  | j&                  | j(                  «      }n.t+        |||| j$                  | j&                  | j(                  «      }t-        j.                  ||«      }	|	j1                  |«      S )
a`  Perform MVDR beamforming.

        Args:
            specgram (torch.Tensor): Multi-channel complex-valued spectrum.
                Tensor with dimensions `(..., channel, freq, time)`
            mask_s (torch.Tensor): Time-Frequency mask of target speech.
                Tensor with dimensions `(..., freq, time)` if multi_mask is ``False``
                or with dimensions `(..., channel, freq, time)` if multi_mask is ``True``.
            mask_n (torch.Tensor or None, optional): Time-Frequency mask of noise.
                Tensor with dimensions `(..., freq, time)` if multi_mask is ``False``
                or with dimensions `(..., channel, freq, time)` if multi_mask is ``True``.
                (Default: None)

        Returns:
            torch.Tensor: Single-channel complex-valued enhanced spectrum with dimensions `(..., freq, time)`.
        é   z?Expected at least 3D tensor (..., channel, freq, time). Found: ziThe type of ``specgram`` tensor must be ``torch.cfloat`` or ``torch.cdouble``.                    Found: Nz=``mask_n`` is not provided, use ``1 - mask_s`` as ``mask_n``.r>   éþÿÿÿ)ÚdeviceÚdtype.)rX   rI   rA   ÚshapeÚ
is_complexr5   ÚcfloatÚcdoubleÚwarningsÚwarnr-   rC   ÚsizerW   r   Úfill_r;   rM   r
   r:   r   r   r   Úapply_beamformingÚto)
r$   r&   rE   rF   rX   r   r   ÚuÚw_mvdrÚspecgram_enhanceds
             r   r.   zMVDR.forward#  s…  € ð& —‘ˆØ�=‰=˜1ÒÜÐ^Ð_g×_mÑ_mÐ^nÐoÓpÐpØ×"Ñ"Ô$ÜðØ$ŸN™NÐ+ð-óð ð �>‰>œUŸ\™\Ò)Ø×'Ñ'Ó)ˆHàˆ>Ü�M‰MÐYÔZØ˜‘ZˆFà—‘˜ 6Ó*ˆØ—‘˜ 6Ó*ˆä�K‰K˜Ÿ™›¨¨Ð,°X·_±_ÌEÏMÉMÔZˆØ	ˆ#ˆt×ÑÐ
Ñ ×&Ñ& qÔ)à�;Š;Ø×2Ñ2Ø�u˜f f¨a°·±À×@QÑ@QÐSW×S`ÑS`ó‰Fô & e¨U°A°t·}±}Àd×FWÑFWÐY]×YfÑYfÓgˆFä×/Ñ/°¸ÓAÐà ×#Ñ# EÓ*Ð*r   )r   r   FTçH¯¼šò×z>F©r   Trf   ç:Œ0âŽyE>r!   )r/   r0   r1   r2   ÚintÚstrr3   r4   r#   r5   r   rM   rK   rL   r   r.   r6   r7   s   @r   r9   r9   a   sŠ  ø„ ñAðJ Ø%Ø Ø!ØØñ!7àð!7ð ð!7ð ð	!7ð
 ð!7ð ð!7ð õ!7ðT &Ø!%ØØñ7oà�|‰|ð7oð �|‰|ð7oð —‘ð	7oð
 —‘ð7oð  Ÿ,™,ð7oð ð7oð ð7oð ð7oð ð7oð 
�‰ó7oðr¨U¯\©\ð À5Ç<Á<ð ÐTY×T`ÑT`ó ð"¨E¯L©Lð À%Ç,Á,ð ÐSX×S_ÑS_ó ð$ ^bñ1+ØŸ™ð1+Ø.3¯l©lð1+ØDLÈUÏ\É\ÑDZð1+à	�‰÷1+r   r9   c                   óJ   — e Zd ZdZ	 	 	 ddedededeeef   dededed	efd
„Z	y)ÚRTFMVDRaÌ  Minimum Variance Distortionless Response (*MVDR* :cite:`capon1969high`) module
    based on the relative transfer function (RTF) and power spectral density (PSD) matrix of noise.

    .. devices:: CPU CUDA

    .. properties:: Autograd TorchScript

    Given the multi-channel complex-valued spectrum :math:`\textbf{Y}`, the relative transfer function (RTF) matrix
    or the steering vector of target speech :math:`\bm{v}`, the PSD matrix of noise :math:`\bf{\Phi}_{\textbf{NN}}`, and
    a one-hot vector that represents the reference channel :math:`\bf{u}`, the module computes the single-channel
    complex-valued spectrum of the enhanced speech :math:`\hat{\textbf{S}}`. The formula is defined as:

    .. math::
        \hat{\textbf{S}}(f) = \textbf{w}_{\text{bf}}(f)^{\mathsf{H}} \textbf{Y}(f)

    where :math:`\textbf{w}_{\text{bf}}(f)` is the MVDR beamforming weight for the :math:`f`-th frequency bin,
    :math:`(.)^{\mathsf{H}}` denotes the Hermitian Conjugate operation.

    The beamforming weight is computed by:

    .. math::
        \textbf{w}_{\text{MVDR}}(f) =
        \frac{{{\bf{\Phi}_{\textbf{NN}}^{-1}}(f){\bm{v}}(f)}}
        {{\bm{v}^{\mathsf{H}}}(f){\bf{\Phi}_{\textbf{NN}}^{-1}}(f){\bm{v}}(f)}
    r&   Úrtfr   Úreference_channelr   r   r   r   c                 óf   — t        j                  ||||||«      }t        j                  ||«      }	|	S )aŠ  
        Args:
            specgram (torch.Tensor): Multi-channel complex-valued spectrum.
                Tensor with dimensions `(..., channel, freq, time)`
            rtf (torch.Tensor): The complex-valued RTF vector of target speech.
                Tensor with dimensions `(..., freq, channel)`.
            psd_n (torch.Tensor): The complex-valued power spectral density (PSD) matrix of noise.
                Tensor with dimensions `(..., freq, channel, channel)`.
            reference_channel (int or torch.Tensor): Specifies the reference channel.
                If the dtype is ``int``, it represents the reference channel index.
                If the dtype is ``torch.Tensor``, its shape is `(..., channel)`, where the ``channel`` dimension
                is one-hot.
            diagonal_loading (bool, optional): If ``True``, enables applying diagonal loading to ``psd_n``.
                (Default: ``True``)
            diag_eps (float, optional): The coefficient multiplied to the identity matrix for diagonal loading.
                It is only effective when ``diagonal_loading`` is set to ``True``. (Default: ``1e-7``)
            eps (float, optional): Value to add to the denominator in the beamforming weight formula.
                (Default: ``1e-8``)

        Returns:
            torch.Tensor: Single-channel complex-valued enhanced spectrum with dimensions `(..., freq, time)`.
        )r   r   ra   )
r$   r&   rm   r   rn   r   r   r   rd   Úspectrum_enhanceds
             r   r.   zRTFMVDR.forwardr  s<   € ô@ ×#Ñ# C¨Ð0AÐCSÐU]Ð_bÓcˆÜ×/Ñ/°¸ÓAÐØ Ð r   N©Trf   rh   )
r/   r0   r1   r2   r   r   ri   r3   r4   r.   © r   r   rl   rl   W  so   „ ñð@ "&ØØñ"!àð"!ð ð"!ð ð	"!ð
 !  f Ñ-ð"!ð ð"!ð ð"!ð ð"!ð 
ô"!r   rl   c                   ó^   — e Zd ZdZ	 	 	 ddedededeeef   dededed	e	j                  fd
„Z
y)Ú
SoudenMVDRa‡  Minimum Variance Distortionless Response (*MVDR* :cite:`capon1969high`) module
    based on the method proposed by *Souden et, al.* :cite:`souden2009optimal`.

    .. devices:: CPU CUDA

    .. properties:: Autograd TorchScript

    Given the multi-channel complex-valued spectrum :math:`\textbf{Y}`, the power spectral density (PSD) matrix
    of target speech :math:`\bf{\Phi}_{\textbf{SS}}`, the PSD matrix of noise :math:`\bf{\Phi}_{\textbf{NN}}`, and
    a one-hot vector that represents the reference channel :math:`\bf{u}`, the module computes the single-channel
    complex-valued spectrum of the enhanced speech :math:`\hat{\textbf{S}}`. The formula is defined as:

    .. math::
        \hat{\textbf{S}}(f) = \textbf{w}_{\text{bf}}(f)^{\mathsf{H}} \textbf{Y}(f)

    where :math:`\textbf{w}_{\text{bf}}(f)` is the MVDR beamforming weight for the :math:`f`-th frequency bin.

    The beamforming weight is computed by:

    .. math::
        \textbf{w}_{\text{MVDR}}(f) =
        \frac{{{\bf{\Phi}_{\textbf{NN}}^{-1}}(f){\bf{\Phi}_{\textbf{SS}}}}(f)}
        {\text{Trace}({{{\bf{\Phi}_{\textbf{NN}}^{-1}}(f) \bf{\Phi}_{\textbf{SS}}}(f))}}\bm{u}
    r&   r   r   rn   r   r   r   r   c                 óf   — t        j                  ||||||«      }t        j                  ||«      }	|	S )a¯  
        Args:
            specgram (torch.Tensor): Multi-channel complex-valued spectrum.
                Tensor with dimensions `(..., channel, freq, time)`.
            psd_s (torch.Tensor): The complex-valued power spectral density (PSD) matrix of target speech.
                Tensor with dimensions `(..., freq, channel, channel)`.
            psd_n (torch.Tensor): The complex-valued power spectral density (PSD) matrix of noise.
                Tensor with dimensions `(..., freq, channel, channel)`.
            reference_channel (int or torch.Tensor): Specifies the reference channel.
                If the dtype is ``int``, it represents the reference channel index.
                If the dtype is ``torch.Tensor``, its shape is `(..., channel)`, where the ``channel`` dimension
                is one-hot.
            diagonal_loading (bool, optional): If ``True``, enables applying diagonal loading to ``psd_n``.
                (Default: ``True``)
            diag_eps (float, optional): The coefficient multiplied to the identity matrix for diagonal loading.
                It is only effective when ``diagonal_loading`` is set to ``True``. (Default: ``1e-7``)
            eps (float, optional): Value to add to the denominator in the beamforming weight formula.
                (Default: ``1e-8``)

        Returns:
            torch.Tensor: Single-channel complex-valued enhanced spectrum with dimensions `(..., freq, time)`.
        )r   r   ra   )
r$   r&   r   r   rn   r   r   r   rd   rp   s
             r   r.   zSoudenMVDR.forward±  s<   € ô@ ×&Ñ& u¨eÐ5FÐHXÐZbÐdgÓhˆÜ×/Ñ/°¸ÓAÐØ Ð r   Nrq   )r/   r0   r1   r2   r   r   ri   r3   r4   r5   r.   rr   r   r   rt   rt   —  sr   „ ñð> "&ØØñ"!àð"!ð ð"!ð ð	"!ð
 !  f Ñ-ð"!ð ð"!ð ð"!ð ð"!ð 
�‰ô"!r   rt   rg   )r]   Útypingr   r   r5   r   Ú
torchaudior   r   Ú__all__rj   r3   r4   r   ÚnnÚModuler   r9   rl   rt   rr   r   r   ú<module>r{      sâ   ðó ß "ã Ý Ý &ð €ð "Ø!ØØñ&Ø�<‰<ð&à�<‰<ð&ð —l‘lð&ð ð	&ð
 ð&ð ð&ð 
ð&ð ‡\�\ó&ôR'ˆ%�(‰(�/‰/ô 'ôTs+ˆ5�8‰8�?‰?ô s+ôl=!ˆe�h‰h�o‰oô =!ô@<!�—‘—‘õ <!r   