o
    i                     @   sN   d dl mZmZmZmZ d dlmZ d dlmZ dd Z	G dd dej
ZdS )    )CallableOptionalTupleUnion)TensorNc                 C   s4   t | trt| dksJ | S t | tsJ | | fS )N   )
isinstancetuplelenint)x r   ?/data/cameron/moge_repo/moge/model/dinov2/layers/patch_embed.pymake_2tuple   s
   
r   c                       s   e Zd ZdZ						ddeeeeef f d	eeeeef f d
ededee de	ddf fddZ
dedefddZdefddZ  ZS )
PatchEmbeda%  
    2D image to patch embedding: (B,C,H,W) -> (B,N,D)

    Args:
        img_size: Image size.
        patch_size: Patch token size.
        in_chans: Number of input image channels.
        embed_dim: Number of linear projection output channels.
        norm_layer: Normalization layer.
                NTimg_size
patch_sizein_chans	embed_dim
norm_layerflatten_embeddingreturnc           
         s   t    t|}t|}|d |d  |d |d  f}	|| _|| _|	| _|	d |	d  | _|| _|| _|| _	t
j||||d| _|rK||| _d S t
 | _d S )Nr      )kernel_sizestride)super__init__r   r   r   patches_resolutionnum_patchesr   r   r   nnConv2dprojIdentitynorm)
selfr   r   r   r   r   r   Zimage_HWZpatch_HWZpatch_grid_size	__class__r   r   r    %   s   
	 zPatchEmbed.__init__r   c                 C   s   |j \}}}}| j\}}|| dksJ d| d| || dks,J d| d| | |}|d|d}}|ddd}| |}| jsV|d	||| j	}|S )
Nr   zInput image height z# is not a multiple of patch height zInput image width z# is not a multiple of patch width: r   r   r   )
shaper   r%   sizeflatten	transposer'   r   reshaper   )r(   r   _HWZpatch_HZpatch_Wr   r   r   forwardD   s   
  

zPatchEmbed.forwardc                 C   sR   | j \}}|| | j | j | jd | jd   }| jd ur'||| | j 7 }|S )Nr   r   )r!   r   r   r   r'   )r(   ZHoZWoflopsr   r   r   r5   S   s
   
(
zPatchEmbed.flops)r   r   r   r   NT)__name__
__module____qualname____doc__r   r   r   r   r   boolr    r   r4   floatr5   __classcell__r   r   r)   r   r      s2    r   )typingr   r   r   r   torchr   torch.nnr#   r   Moduler   r   r   r   r   <module>   s
   		