o
    ¡¿¯iF
  ã                   @   s@   d dl Z d dlmZ d dlmZ d dlmZ G dd„ deƒZdS )é    N)Ú
AbsEnhLoss)ÚAbsLossWrapper)Ú	PITSolverc                       s4   e Zd Z		ddef‡ fdd„Zi fdd„Z‡  ZS )	ÚMultiLayerPITSolverç      ð?TÚ	criterionc                    s.   t ƒ  ¡  || _|| _|| _t|||ƒ| _dS )a%  Multi-Layer Permutation Invariant Training Solver.

        Compute the PIT loss given inferences of multiple layers and a single reference.
        It also support single inference and single reference in evaluation stage.

        Args:
            criterion (AbsEnhLoss): an instance of AbsEnhLoss
            weight (float): weight (between 0 and 1) of current loss
                for multi-task learning.
            independent_perm (bool):
                If True, PIT will be performed in forward to find the best permutation;
                If False, the permutation from the last LossWrapper output will be
                inherited.
                Note: You should be careful about the ordering of loss
                wrappers defined in the yaml config, if this argument is False.
        N)ÚsuperÚ__init__r   ÚweightÚindependent_permr   Úsolver)Úselfr   r
   r   ©Ú	__class__© úc/home/ubuntu/.local/lib/python3.10/site-packages/espnet2/enh/loss/wrappers/multilayer_pit_solver.pyr	   	   s
   
zMultiLayerPITSolver.__init__c           	      C   s”   d}t  |d ¡rt|ƒt|ƒkr|  |||¡\}}}|}n't|ƒD ]\}}|  |||¡\}}}|||d  dt|ƒ   }q"|t|ƒ }|||fS )aÐ  Permutation invariant training solver.

        Args:
            ref (List[torch.Tensor]): [(batch, ...), ...] x n_spk
            infs (Union[List[torch.Tensor], List[List[torch.Tensor]]]):
                [(batch, ...), ...]

        Returns:
            loss: (torch.Tensor): minimum loss with the best permutation
            stats: dict, for collecting training status
            others: dict, in this PIT solver, permutation order will be returned
        g        r   é   r   )ÚtorchÚ	is_tensorÚlenr   Ú	enumerate)	r   ÚrefÚinfsÚothersÚlossesÚlossÚstatsÚidxÚinfr   r   r   Úforward%   s   
zMultiLayerPITSolver.forward)r   T)Ú__name__Ú
__module__Ú__qualname__r   r	   r   Ú__classcell__r   r   r   r   r      s    üþr   )r   Ú$espnet2.enh.loss.criterions.abs_lossr   Ú%espnet2.enh.loss.wrappers.abs_wrapperr   Ú$espnet2.enh.loss.wrappers.pit_solverr   r   r   r   r   r   Ú<module>   s
    