o
    yi                     @   s  d dl mZmZ d dlZd dlm  mZ d dlmZ d dl	m
Z
 d dlmZ dededejd	ejd
ef
ddZdedee dee dejd	eejef d
efddZdedee dee dejd	ejd
efddZdededed
efddZdedededed
ef
ddZdS )    )SequenceUnionN)Tensor)rank_zero_warn)_TORCH_GREATER_EQUAL_1_10kernel_sizesigmadtypedevicereturnc                 C   sT   t jd|  d d|  d d||d}t t || d d }||  jddS )aY  Computes 1D gaussian kernel.

    Args:
        kernel_size: size of the gaussian kernel
        sigma: Standard deviation of the gaussian kernel
        dtype: data type of the output tensor
        device: device of the output tensor

    Example:
        >>> _gaussian(3, 1, torch.float, 'cpu')
        tensor([[0.2741, 0.4519, 0.2741]])
          )startendstepr	   r
   r   )dim)torcharangeexppowsum	unsqueeze)r   r   r	   r
   distgauss r   X/home/ubuntu/.local/lib/python3.10/site-packages/torchmetrics/functional/image/helper.py	_gaussian   s   $r   channelc                 C   sT   t |d |d ||}t |d |d ||}t| |}|| d|d |d S )a  Computes 2D gaussian kernel.

    Args:
        channel: number of channels in the image
        kernel_size: size of the gaussian kernel as a tuple (h, w)
        sigma: Standard deviation of the gaussian kernel
        dtype: data type of the output tensor
        device: device of the output tensor

    Example:
        >>> _gaussian_kernel_2d(1, (5,5), (1,1), torch.float, "cpu")
        tensor([[[[0.0030, 0.0133, 0.0219, 0.0133, 0.0030],
                  [0.0133, 0.0596, 0.0983, 0.0596, 0.0133],
                  [0.0219, 0.0983, 0.1621, 0.0983, 0.0219],
                  [0.0133, 0.0596, 0.0983, 0.0596, 0.0133],
                  [0.0030, 0.0133, 0.0219, 0.0133, 0.0030]]]])
    r   r   )r   r   matmultexpand)r   r   r   r	   r
   gaussian_kernel_xgaussian_kernel_ykernelr   r   r   _gaussian_kernel_2d   s   r$   c           
   	   C   s   t |d |d ||}t |d |d ||}t |d |d ||}t| |}t|ddd|d ||d |d |d }	|	| d|d |d |d S )a6  Computes 3D gaussian kernel.

    Args:
        channel: number of channels in the image
        kernel_size: size of the gaussian kernel as a tuple (h, w, d)
        sigma: Standard deviation of the gaussian kernel
        dtype: data type of the output tensor
        device: device of the output tensor
    r   r   r   )r   r   r   r   mulr   repeatr    )
r   r   r   r	   r
   r!   r"   gaussian_kernel_z	kernel_xyr#   r   r   r   _gaussian_kernel_3d=   s   r*   inputsr   padc              
   C   s`   | j | d }t| |tj|dd| jd}t| |tj||| d| jd}t|| |f|S )zReflective padding of input along a specific dimension.

    Args:
        inputs: tensor to pad
        dim: dimension to pad along
        pad: amount of padding to add

    Returns:
        padded input
    r   r   r%   )r
   )shaper   index_selectr   r
   cat)r+   r   r,   _maxxyr   r   r   _single_dimension_padU   s   "r3   pad_hpad_wpad_dc                 C   sX   t rtj| ||||||fdd} | S td t|||gD ]\}}t| |d |} q| S )aT  Reflective padding of 3d input.

    Args:
        inputs: tensor to pad, should be a 3D tensor of shape ``[N, C, H, W, D]``
        pad_w: amount of padding in the height dimension
        pad_h: amount of padding in the width dimension
        pad_d: amount of padding in the depth dimension

    Returns:
        padded input tensor
    reflect)modez`An older version of pyTorch is used. For optimal speed, please upgrade to at least pyTorch 1.10.r   )r   Fr,   r   	enumerater3   )r+   r4   r5   r6   r   r,   r   r   r   _reflection_pad_3df   s   r;   )typingr   r   r   torch.nn.functionalnn
functionalr9   r   torchmetrics.utilitiesr   torchmetrics.utilities.importsr   intfloatr	   r
   r   strr$   r*   r3   r;   r   r   r   r   <module>   sF    "
 
"