o
    .wiF                     @   s^   d dl Z d dl mZ deddfddZdedeeef fddZdedeeef fd	d
ZdS )    N)Tensorimgreturnc                 C   s<   t | tstdt|  | jdkrtd| j ddS )z*Validate whether img is a 4D torch Tensor.z3The `img` expects a value of <Tensor> type but got    z&The `img` expects a 4D tensor but got zD tensorN)
isinstancer   	TypeErrortypendimRuntimeErrorr    r   d/home/ubuntu/sommelier/.venv/lib/python3.10/site-packages/torchmetrics/functional/image/gradients.py_image_gradients_validate   s
   

r   c           	      C   s   | j \}}}}| dddddf | dddddf  }| dddddf | dddddf  }||d|g}tj|tj|| j| jdgdd}|| j }|||dg}tj|tj|| j| jdgdd}|| j }||fS )	z2Compute image gradients (dy/dx) for a given image..   N)devicedtype   )dim   )shapetorchcatzerosr   r   view)	r   
batch_sizechannelsheightwidthdydxshapeyshapexr   r   r   _compute_image_gradients   s   ,,""r#   c                 C   s   t |  t| S )a  Compute `Gradient Computation of Image`_ of a given image using finite difference.

    Args:
        img: An ``(N, C, H, W)`` input tensor where ``C`` is the number of image channels

    Return:
        Tuple of ``(dy, dx)`` with each gradient of shape ``[N, C, H, W]``

    Raises:
        TypeError:
            If ``img`` is not of the type :class:`~torch.Tensor`.
        RuntimeError:
            If ``img`` is not a 4D tensor.

    Example:
        >>> from torchmetrics.functional.image import image_gradients
        >>> image = torch.arange(0, 1*1*5*5, dtype=torch.float32)
        >>> image = torch.reshape(image, (1, 1, 5, 5))
        >>> dy, dx = image_gradients(image)
        >>> dy[0, 0, :, :]
        tensor([[5., 5., 5., 5., 5.],
                [5., 5., 5., 5., 5.],
                [5., 5., 5., 5., 5.],
                [5., 5., 5., 5., 5.],
                [0., 0., 0., 0., 0.]])

    .. note::
           The implementation follows the 1-step finite difference method as followed
           by the TF implementation. The values are organized such that the gradient of
           [I(x+1, y)-[I(x, y)]] are at the (x, y) location

    )r   r#   r   r   r   r   image_gradients-   s   !r$   )r   r   r   tupler#   r$   r   r   r   r   <module>   s
   