o
    piO-                     @   sJ   d dl Z d dlZddlmZ ddlmZ ddlmZm	Z	 G dd dZ
dS )    N   )common_functions)loss_tracker)
KeyCheckerKeyCheckerDictc                   @   s^  e Zd Z																		dQddZdd	 Zd
d Zdd ZdRddZdd Zdd Z	dd Z
dd Zdd Zdd Zdd Zdd  Zd!d" Zd#d$ Zd%d& Zd'd( ZdSd)d*Zd+d, Zd-d. Zd/d0 Zd1d2 Zd3d4 Zd5d6 Zd7d8 Zd9d: Zd;d< Zd=d> Zd?d@ ZdAdB Z dCdD Z!dEdF Z"dGdH Z#dIdJ Z$dKdL Z%dMdN Z&dOdP Z'dS )TBaseTrainerN Fr   r   c                 C   s   || _ || _|| _|| _|| _|d u ri n|| _|| _|| _|	| _|| _	|| _
|| _|| _|| _|| _|| _|| _|
| _|| _|| _|| _|| _|| _t| j | _|   |   |   |   |   |   |    | !  | "  | #  d S N)$models
optimizers
batch_size
loss_funcsdatasetmining_funcsiterations_per_epochdata_devicedtypesampler
collate_fnlr_schedulersgradient_clippersfreeze_thesefreeze_trunk_batchnormlabel_hierarchy_leveldataloader_num_workersloss_weightsdata_and_label_getterdataset_labelsset_min_label_to_zeroend_of_iteration_hookend_of_epoch_hooklistkeys
loss_namescustom_setupverify_dict_keysinitialize_modelsinitialize_data_deviceinitialize_label_mapperinitialize_loss_trackerinitialize_loss_weights initialize_data_and_label_getterinitialize_hooksinitialize_lr_schedulers)selfr
   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r    r   r   a/home/ubuntu/.local/lib/python3.10/site-packages/pytorch_metric_learning/trainers/base_trainer.py__init__
   sD   zBaseTrainer.__init__c                 C      d S r	   r   r.   r   r   r/   r$   G      zBaseTrainer.custom_setupc                 C   s   t r	   )NotImplementedErrorr2   r   r   r/   calculate_lossJ   r3   zBaseTrainer.calculate_lossc                 C   r1   r	   r   r2   r   r   r/   update_loss_weightsM   r3   zBaseTrainer.update_loss_weights   c                 C   s   |    t||d D ]K| _|   tjd| j  tt| j}|D ]| _	| 
  | |  |d| jd   | jdd q%| jdd |   | | du rV d S qd S )Nr7   zTRAINING EPOCH %dztotal_loss=%.5f
total_lossF)end_of_epochT)initialize_dataloaderrangeepochset_to_trainc_fLOGGERinfotqdmr   	iterationforward_and_backwardr   set_descriptionlossesstep_lr_schedulerszero_lossesr    )r.   start_epoch
num_epochspbarr   r   r/   trainP   s    

zBaseTrainer.trainc                 C   sd   t jd t | j| j| j| j| j| _	| j
st| j	| _
t jd t| j	| _t jd d S )NzInitializing dataloaderz Initializing dataloader iteratorz!Done creating dataloader iterator)r>   r?   r@   get_train_dataloaderr   r   r   r   r   
dataloaderr   leniterdataloader_iterr2   r   r   r/   r:   `   s   z!BaseTrainer.initialize_dataloaderc                 C   sP   |    |   |   | |   | j| j |   | 	  | 
  d S r	   )rG   	zero_gradr6   r5   	get_batchr   updater   backwardclip_gradientsstep_optimizersr2   r   r   r/   rC   o   s   z BaseTrainer.forward_and_backwardc                 C   s   | j  D ]}d| j |< qd S )Nr   )rE   r"   )r.   kr   r   r/   rG   y   s   zBaseTrainer.zero_lossesc                 C   s4   | j  D ]}|  q| j D ]}|  qd S r	   )r
   valuesrQ   r   r.   vr   r   r/   rQ   }   s
   

zBaseTrainer.zero_gradc                 C   sB   t | j| j\| _}| |\}}t || j| j}| ||S r	   )	r>   try_next_on_generatorrP   rM   r   process_labelr   label_mappermaybe_do_batch_mining)r.   
curr_batchdatalabelsr   r   r/   rR      s   

zBaseTrainer.get_batchc                 C   s   |  |}| |}|S r	   )get_trunk_outputget_final_embeddings)r.   r`   trunk_output
embeddingsr   r   r/   compute_embeddings   s   

zBaseTrainer.compute_embeddingsc                 C   s   | j d |S Nembedder)r
   )r.   base_outputr   r   r/   rc      s   z BaseTrainer.get_final_embeddingsc                 C   s"   t j|| j| jd}| jd |S )N)devicer   trunk)r>   	to_devicer   r   r
   )r.   r`   r   r   r/   rb      s   zBaseTrainer.get_trunk_outputc                 C   s   d| j v r| j d ||S d S )Ntuple_miner)r   )r.   re   ra   r   r   r/   maybe_mine_embeddings   s   
z!BaseTrainer.maybe_mine_embeddingsc                 C   s|   d| j v r:t ) |   | |}| j d ||}|   || || }}W d    ||fS 1 s5w   Y  ||fS )Nsubset_batch_miner)r   torchno_gradset_to_evalrf   r=   )r.   r`   ra   re   idxr   r   r/   r^      s   



z!BaseTrainer.maybe_do_batch_miningc                 C   s   | j d   d S )Nr8   )rE   rT   r2   r   r   r/   rT      s   zBaseTrainer.backwardc                 C   s   | j | j| jd   S )Nr7   )rB   r   r<   r2   r   r   r/   get_global_iteration   s   z BaseTrainer.get_global_iterationc                 C   s`   | j d ur,| j  D ]#\}}|r|| jd r|  q
|s+|| jd r+|  q
d S d S )Nr<   rB   r   itemsendswith!allowed_lr_scheduler_key_suffixesstep)r.   r9   rW   rZ   r   r   r/   rF      s   

zBaseTrainer.step_lr_schedulersc                 C   s@   | j d ur| j  D ]\}}|| jd r|| q
d S d S )Nplateauru   )r.   validation_inforW   rZ   r   r   r/   step_lr_plateau_schedulers   s   

z&BaseTrainer.step_lr_plateau_schedulersc                 C   s4   | j  D ]\}}tdd|| jvr|  qd S )Nz_optimizer$ )r   rv   r>   regex_replacer   ry   )r.   rW   rZ   r   r   r/   rV      s
   zBaseTrainer.step_optimizersc                 C   s(   | j d ur| j  D ]}|  q
d S d S r	   )r   rX   rY   r   r   r/   rU      s
   
zBaseTrainer.clip_gradientsc                 C   s$   | j r| jd td d S d S )Nrk   	BatchNorm)r   r
   applyr>   set_layers_to_evalr2   r   r   r/   maybe_freeze_trunk_batchnorm   s   z(BaseTrainer.maybe_freeze_trunk_batchnormc                 C   s   | j d u rt | _ d S d S r	   )r   r>   use_cuda_if_availabler2   r   r   r/   r'      s   
z"BaseTrainer.initialize_data_devicec                 C   s   t | j| jj| _d S r	   )r>   LabelMapperr   r   mapr]   r2   r   r   r/   r(      s
   z#BaseTrainer.initialize_label_mapperc                 C   s   t | j| _| jj| _d S r	   )l_tLossTrackerr#   r   rE   r2   r   r   r/   r)      s   z#BaseTrainer.initialize_loss_trackerc                 C   s   | j d u rtj| _ d S d S r	   )r   r>   return_inputr2   r   r   r/   r+      s   
z,BaseTrainer.initialize_data_and_label_getterc                 C   s   | j | jgS r	   r
   r   r2   r   r   r/   trainable_attributes   s   z BaseTrainer.trainable_attributesc                 C   sV   |   D ] }| D ]\}}|| jv rtj|dd |  q
|  q
q|   d S )NF)requires_grad)r   rv   r   r>   set_requires_gradevalrK   r   )r.   TrW   rZ   r   r   r/   r=      s   


zBaseTrainer.set_to_trainc                 C   s(   |   D ]}| D ]}|  q
qd S r	   )r   rX   r   )r.   r   rZ   r   r   r/   rr      s
   
zBaseTrainer.set_to_evalc                 C   s$   | j d u rdd | jD | _ d S d S )Nc                 S   s   i | ]}|d qS )r7   r   ).0rW   r   r   r/   
<dictcomp>   s    z7BaseTrainer.initialize_loss_weights.<locals>.<dictcomp>)r   r#   r2   r   r   r/   r*      s   
z#BaseTrainer.initialize_loss_weightsc                 C   s,   | j d u r	tj| _ | jd u rtj| _d S d S r	   )r   r>   r   r    r2   r   r   r/   r,      s
   

zBaseTrainer.initialize_hooksc                 C   s   | j d u r
i | _ d S d S r	   )r   r2   r   r   r/   r-      s   

z$BaseTrainer.initialize_lr_schedulersc                 C   s"   d| j vrtj | j d< d S d S rg   )r
   rp   nnIdentityr2   r   r   r/   r&      s   
zBaseTrainer.initialize_modelsc                 C   s.   dddd| _ |   | j|  |   d S )N_scheduler_by_iteration_scheduler_by_epoch_scheduler_by_plateau)rB   r<   rz   )rx   
set_schemaschemaverifyverify_freeze_these_keysr2   r   r   r/   r%     s   zBaseTrainer.verify_dict_keysc                 C   r1   r	   r   r2   r   r   r/   modify_schema  r3   zBaseTrainer.modify_schemac                    s   t tddgdgdtdgtddgdg dt jd jd	td
d t j ddt fdddg dtdd dg dd _   d S )Nrk   rh   )	essentialmetric_lossro   rm   F)
warn_empty	important)r   r   c                 S      t |d j|d j dS )Nr
   r   
_optimizerr>   
append_mapr"   sdr   r   r/   <lambda>      z(BaseTrainer.set_schema.<locals>.<lambda>r   )r   c                    s    fddj  D S )Nc                    s.   g | ]} d  j  d j  D ]}|| qqS r   )r"   )r   yxr   r   r/   
<listcomp>$  s    z<BaseTrainer.set_schema.<locals>.<lambda>.<locals>.<listcomp>)rx   rX   r   r2   r   r/   r   $  s   
 c                 S   r   )Nr
   r   _grad_clipperr   r   r   r   r/   r   -  r   )r
   r   r   r   r   r   r   )	r   r   r#   r>   r   r
   r"   r   r   r2   r   r2   r/   r     s8   

	$zBaseTrainer.set_schemac                 C   sh   | j d j| j d j }| jD ]"}||v sJ dd||d | j v r1tjd| qd S )Nr
   r   z#freeze_these keys must be one of {}z, r   zHYou have passed in an optimizer for {}, but are freezing its parameters.)	r   r"   r   formatjoinr   r>   r?   warning)r.   allowed_keysrW   r   r   r/   r   7  s   
z$BaseTrainer.verify_freeze_these_keys)NNNNNNNNNr   Fr   r   NNFNN)r7   r7   )F)(__name__
__module____qualname__r0   r$   r5   r6   rK   r:   rC   rG   rQ   rR   rf   rc   rb   rn   r^   rT   rt   rF   r|   rV   rU   r   r'   r(   r)   r+   r   r=   rr   r*   r,   r-   r&   r%   r   r   r   r   r   r   r/   r   	   sp    
=






'r   )rp   rA   utilsr   r>   r   r   utils.key_checkerr   r   r   r   r   r   r/   <module>   s    