o
    xi                     @   s|   d dl Z d dlZd dlmZ edjZdd Zdd Z	e j
ddd	d
 ZdddZdd Zdd ZdddZdd ZdS )    N)resample_polyfloatc                 C   s   t | |}|dkr| | } || }d}ddt| |  }|d }d| }t |d d|  }t | |d }d|  | t d| |  }	|d	kr_|d
kr_d|d	 d  d|d	   }
n|d
krjd|d  }
nd}
t d| d |
|	 }|S )zPort of Octave code to Python   g            ?   
   i   gX9ȶ<@   2   gW2ı?g?gUj@+0?gK46?gffffff!@g        )npgcdmaxceilarangesinckaiser)pqr   log10_rejectionstopband_cutoff_froll_off_widthrejection_dBLtideal_filterbetah r   @/home/ubuntu/.local/lib/python3.10/site-packages/pystoi/utils.py_resample_window_oct	   s,   

r   c                 C   s(   t ||}|t| }t| |||dS )z(Resampler that is compatible with Octave)window)r   r   sumr   )xr   r   r   r    r   r   r   resample_oct.   s   
r#   )maxsizec                 C   s  t d| |d }|dt|d d  }t t|t}t d|| }|t dd| d d  }|t dd| d d  }t |t	|f}	tt	|D ]2}
t 
t |||
  }|| ||
< |}t 
t |||
  }|| ||
< |}d|	|
||f< qR|	|fS )aJ   Returns the 1/3 octave band matrix and its center frequencies
    # Arguments :
        fs : sampling rate
        nfft : FFT size
        num_bands : number of 1/3 octave bands
        min_freq : center frequency of the lowest 1/3 octave band
    # Returns :
        obm : Octave Band Matrix
        cf : center frequencies
    r   r   Nr   gr(?g       @   )r   linspaceintarrayrangeastyper   powerzeroslenargminsquare)fsnfft	num_bandsmin_freqfkcffreq_low	freq_highobmif_binfl_iifh_iir   r   r   thirdoct5   s    r>      c                    sT   t | }td dd t fddtdt |D }|S )a   Short-time Fourier transform for real 1-D inputs
    # Arguments
        x : 1D array, the waveform
        win_size : integer, the size of the window and the signal frames
        fft_size : integer, the size of the fft in samples (zero-padding or not)
        overlap: integer, number of steps to make in fftsize
    # Returns
        stft_out : 2D complex array, the STFT of x.
    r   r   c                    s,   g | ]}t jj||    d qS ))n)r   fftrfft.0r:   fft_sizewwin_sizer"   r   r   
<listcomp>b   s    $zstft.<locals>.<listcomp>r   )r'   r   hanningr(   r)   r-   )r"   rI   rG   overlaphopstft_outr   rF   r   stftV   s   
rO   c                 C   s   | j \}}| |  }t| d|fd|| | ff}||| ||f}t|g d}|d|f}|d |  }|||| d |f}tj|dd}t| d | | }|dd | }|S )Nr   )r   r   r   r@   r   axis)shaper   padreshape	transposer!   r-   )x_framesrM   
num_framesframelensegmentssignalendr   r   r   _overlap_and_addg   s   
 r\   c                    s   t  d dd t  fddtdt  |D }t  fddtdt  |D }dt t jj|dd	t  }t 	|| | dk }|| }|| }t
||}	t
||}
|	|
fS )
a9   Remove silent frames of x and y based on x
    A frame is excluded if its energy is lower than max(energy) - dyn_range
    The frame exclusion is based solely on x, the clean speech signal
    # Arguments :
        x : array, original speech wav file
        y : array, denoised speech wav file
        dyn_range : Energy range to determine which frame is silent
        framelen : Window size for energy evaluation
        hop : Hop size for energy evaluation
    # Returns :
        x without the silent frames
        y without the silent frames (aligned to x)
    r   r   r@   c                        g | ]}||    qS r   r   rD   )rX   rH   r"   r   r   rJ           z(remove_silent_frames.<locals>.<listcomp>r   c                    r]   r   r   rD   )rX   rH   yr   r   rJ      r^      rP   )r   rK   r(   r)   r-   log10linalgnormEPSr   r\   )r"   r_   	dyn_rangerX   rM   rV   y_frames
x_energiesmaskx_sily_silr   )rX   rH   r"   r_   r   remove_silent_frames   s   $$

rk   r@   c                 C   s   t jt | |ddS )zL Returns an array of vectors of norms of the rows of matrices from 3D array TrQ   keepdims)r   r!   r/   )r"   rQ   r   r   r   vect_two_norm   s   rn   c                    s   | t tj| j  }|tj|ddd8 }dtt|  t fddt	 jd D }t
||}|t 
 tj|j 7 }|tj|ddd8 }dtt|dd	  t fd
dt	 jd D }t
||}|S )zD Row and column mean and variance normalize an array of 2D segments r@   Trl   r   c                        g | ]}t  | d qS r@   r   diagrT   rD   x_invr   r   rJ      r^   z%row_col_normalize.<locals>.<listcomp>r   r   rP   c                    ro   rp   rq   rD   rs   r   r   rJ      r^   )rd   r   randomstandard_normalrR   meansqrtrn   r(   r)   matmul)r"   x_normedx_diagsr   rs   r   row_col_normalize   s   r|   )r?   rp   )	functoolsnumpyr   scipy.signalr   finfoepsrd   r   r#   	lru_cacher>   rO   r\   rk   rn   r|   r   r   r   r   <module>   s    %


 
'