Quelques astuces de pytorch
changelog
- 29 novembre 2019: Mise à jour de certaines techniques de conception de modèles et du contenu d'accélération du raisonnement, et a ajouté un lien d'introduction vers l'Apex,
De plus, j'ai supprimé tfrecord, peut-on utiliser pytorch? Je me souviens que je ne peux pas, alors je l'ai supprimé (Indique la suppression: <) - 30 novembre 2019: Signification de Mac supplémentaire, Lien papier de ShuffleNeTV2 supplémentaire
- 2 décembre 2019: le pytorch que j'ai mentionné plus tôt ne peut pas utiliser tfrecord. Aujourd'hui, j'ai vu une réponse de https://www.zhihu.com/question/358632497, et je suis dans une posture croissante.
- 23 décembre 2019: Ajout de plusieurs articles scientifiques populaires sur la quantification de la compression du modèle
- 7 février 2020: quelques choses à noter ont été extraites de l'article et ajoutées à la section Niveau de code
- 30 avril 2020:
- Ajout d'une sauvegarde de document de github
- Liens complétés à l'introduction de la couche convolutionnelle et de la fusion de la couche BN
- Voici une autre explication. Pour les articles et réponses de nombreux amis que j'ai référencés auparavant, les liens et le résumé de contenu correspondant ne sont pas liés entre eux. On estime que certains amis poseront des questions lors de la lecture du contenu lié, et ils ne peuvent pas demander à l'auteur d'origine. Je suis profondément désolé ici.
- Ajustez un contenu et essayez de correspondre au lien de référence
- 18 mai 2020: Ajoutez quelques conseils sur Pytorch pour enregistrer la mémoire vidéo. En même temps, ajustez simplement le format. J'ai également trouvé une erreur précédente: la suggestion
non_blocking=False devrait être non_blocking=True . - 6 janvier 2021: Ajustez quelques introductions sur la lecture des données de l'image.
- 13 janvier 2021: Ajout d'une stratégie de raisonnement accéléré. Je pense que je devrais d'abord mettre à jour le document GitHub. La mise à jour des réponses de Zhihu est un peu gênante, et il est impossible de comparer le changement d'information, c'est donc très difficile.
- 26 juin 2022: Le format suivant et la disposition du contenu ont été réajustés, tandis que des références supplémentaires et certaines des dernières découvertes ont été ajoutées.
- 20 juin 2024: L'ajustement simple du format est complété avec une idée pour accélérer la lecture des données basée sur le format
tar et IterableDataset .
Pytorch accélérer
Note
Document original: https://www.yuque.com/lart/ugkv9f/ugysgn
Déclaration: La plupart du contenu provient du partage sur Zhihu et d'autres blogs, et n'est répertorié ici que comme collection. Plus de suggestions sont les bienvenues.
Réponse zhihu (bienvenue à aimer):
- Le chargement des données de Pytorch DatalOader prend la plupart du temps. Comment le résolvez-vous? - Réponse de l'artiste du peuple - Zhihu
- Lorsque vous utilisez Pytorch, il y a trop de données de formation de formation pour atteindre des dizaines de millions, et que dois-je faire si le dataloader se charge très lentement? - Réponse de l'artiste du peuple - Zhihu
Le prétraitement accélère
- Pour minimiser les opérations de prétraitement chaque fois que vous lisez des données, vous pouvez envisager d'utiliser des opérations fixes, telles que
resize , et les enregistrer à l'avance, et les utiliser directement pendant la formation. - Déplacez le prétraitement vers le GPU pour accélérer.
- Linux peut utiliser
NVIDIA/DALI . - Utilisez des opérations de traitement d'image basées sur le tenseur.
IO accélére
- MMCV fournit une prise en charge relativement efficace et complète de la lecture des données: OpenMMLAB: MMCV Core Component Analysis (III): FileClient
Utilisez un traitement d'image plus rapide
-
opencv est généralement plus rapide que PIL .- Notez que la stratégie de chargement paresseuse de
PIL le rend open que imread d' opencv , mais en fait, il ne charge pas complètement les données. Vous pouvez appeler la méthode load() sur l'objet renvoyé par open to Load Data manuellement. La vitesse est raisonnable à ce moment.
- Pour
jpeg Reads, vous pouvez essayer jpeg4py . - Enregistrez le graphique
bmp (réduisez le temps de décodage). - Discussion sur la vitesse des différentes bibliothèques de traitement d'images: Quelle est la différence entre la méthode d'implémentation et la vitesse de lecture des différentes fonctions IMRead de Python? - Zhihu
Intégrer les données dans un seul fichier continu (réduire le nombre de lectures)
Pour les lectures de petits fichiers à grande échelle, il peut être enregistré comme un format de fichier continu qui peut être lu en continu. Vous pouvez choisir de considérer TFRecord (Tensorflow) , recordIO , hdf5 , pth , n5 , lmdb , etc.
-
TFRecord : https://github.com/vahidk/tfrecord - Base de données
lmdb :- https://github.com/fangyh09/image2lmdb
- https://blog.csdn.net/p_lart/article/details/103208405
- https://github.com/lartpang/pysodtoolbox/blob/master/forbigdataset/imagefolder2lmdb.py
- Implémentation basée sur le fichier
Tar et IterableDataset
Données pré-lis
Pré-lecture des données requises pour la prochaine itération. Cas d'utilisation:
- Comment vous donner le DatalOader à Pytorch - Articles MKFMIKU - Zhihu
- Accélérer les données de lecture à Pytorch - Articles sur Hi - Zhihu
Avec mémoire
- Chargez directement dans la mémoire.
- Lisez l'image et enregistrez-la dans un objet de conteneur fixe.
- Carte Mémoire au disque.
À l'état solide
Le disque dur mécanique est remplacé par un état solide NVME. Reportez-vous à la façon de vous donner un sang de poulet dans le dataloader à Pytorch - Article de Mkfmiku - Zhihu
Stratégies de formation
Formation à faible précision
Dans la formation, les représentations à faible précision ( FP16 ou même INT8 , réseau binaire et réseau à trois valeurs) sont utilisées à la place des représentations de précision d'origine ( FP32 ).
Il peut économiser une certaine quantité de mémoire vidéo et accélérer, mais faites attention aux opérations dangereuses telles que la moyenne et la somme.
- Introduction à la formation de précision mixte:
- Tutoriel de formation de précision mixte de peu profond à profond
- Support de précision mixte fourni par
NVIDIA/Apex .- Artefact incontournable pytorch | Fast-Free: Accélération de précision hybride basée sur Apex
- Installation pytorch d'Apex Solutions de maladie difficile et diverses - Articles de Chen Hanke - Zhihu
- Pytorch1.6 commence à fournir
torch.cuda.amp pour soutenir une précision mixte.
Un plus gros lot
Les lots plus importants ont tendance à conduire à un temps de formation plus court dans le cas de l'époque fixe. Cependant, les grands lots sont confrontés à de nombreuses considérations telles que le réglage de l'hyperparamètre et l'utilisation de la mémoire, qui est un autre domaine qui a attiré beaucoup d'attention.
- Paramètres d'hyperparamètre
- SGD à minibatch précis et grand: formation d'imaget en 1 heure, papier
- Optimiser l'utilisation de la mémoire vidéo
- Accumulation de gradient
- Poignage de contrôle du gradient
- Formation des filets profonds avec coût de mémoire sous-linéaire, papier
- Opération sur place
- Batchnorm activé en place pour la formation optimisée à la mémoire des DNN, papiers, code
Niveau de code
Paramètres de la bibliothèque
- Définir
torch.backends.cudnn.benchmark = True avant que la boucle d'entraînement puisse accélérer le calcul. Étant donné que les performances des algorithmes CUDNN qui calculent les convolutions de différentes tailles de noyau diffèrent, l'autotuner peut exécuter une référence pour trouver le meilleur algorithme. Il est recommandé d'activer ce paramètre lorsque votre taille d'entrée ne change pas fréquemment. Si la taille de l'entrée change fréquemment, l'autotuner devra être trop souvent comparé, ce qui peut nuire aux performances. Il peut augmenter la vitesse de propagation vers l'avant et vers l'arrière de 1,27x à 1,70x. - Utilisez la page pour verrouiller la mémoire, c'est-à-dire définir
pin_memory=True dans DatalOader. - Pour un nombre approprié
num_worker , des discussions détaillées peuvent être trouvées dans le guide Pytorch SpeedUp - Articles de Yunmeng - Zhihu. - optimizer.zero_grag (set_to_none = false ici vous pouvez réduire l'empreinte de la mémoire en définissant
set_to_none=True et peut améliorer modérément les memset . Mais cela changera également un comportement, qui est visible par la documentation. memset est effectué sur None les paramètres model.zero_grad() ou optimizer.zero_grad() Le gradient sera mis None jour à l'aide de l'opération "Écrire uniquement". - Pendant la rétropropagation, utilisez le mode
eval et utilisez torch.no_grad pour désactiver les calculs du gradient. - Envisagez d'utiliser le format de mémoire Channels_Last.
- Remplacez
DataParallel avec DistributedDataParallel . Pour le multi-GPU, même s'il DataParallel a qu'un seul nœud, DistributedDataParallel est toujours préféré car DistributedDataParallel est appliqué à plusieurs processus et en crée un pour chaque GPU, contournant le verrouillage interprète global Python (GIL) et la vitesse croissante.
Modèle
- N'initialisez pas les variables inutilisées, car l'initialisation et
forward de Pytorch sont séparés, et il n'initialisera pas car vous ne les utilisez pas. -
@torch.jit.script , utilisez Pytroch Jit pour fusionner des opérations point par point sur un seul noyau Cuda. Pytorch optimise le fonctionnement des tenseurs avec de grandes dimensions. Il est très inefficace de faire trop d'opérations sur de petits tenseurs en pytorch. Donc, si possible, la réécriture de toutes les opérations de calcul en lots peut réduire la consommation et améliorer les performances. Si vous ne pouvez pas implémenter manuellement les opérations par lots, TorchScript peut être utilisé pour améliorer les performances de votre code. TorchScript est un sous-ensemble de fonctions Python, mais après que Pytorch soit vérifié par Pytorch, Pytorch peut automatiquement optimiser le code TORCHScript pour améliorer les performances via son compilateur Just In Time (JTT). Mais une meilleure approche consiste à mettre en œuvre manuellement les opérations par lots. - Lorsque vous utilisez FP16 avec une précision mixte, définissez un multiple de taille 8 pour toutes les différentes conceptions architecturales.
- La couche convolutionnelle avant BN peut supprimer le biais. Parce que mathématiquement, le biais peut être compensé au moyen de la soustraction de BN. Nous pouvons enregistrer les paramètres du modèle et la mémoire d'exécution.
données
- Réglez la taille du lot sur un multiple de 8 pour maximiser l'utilisation de la mémoire GPU.
- Effectuez autant que possible les opérations de style numpy sur le GPU.
- Utilisez
del pour libérer l'empreinte mémoire. - Évitez la transmission de données inutile entre différents appareils.
- Lors de la création d'un tenseur, spécifiez directement l'appareil, au lieu de le créer, puis de le transférer sur le périphérique cible.
- Utilisez
torch.from_numpy(ndarray) ou torch.as_tensor(data, dtype=None, device=None) , qui peut éviter de réappliquer l'espace en partageant la mémoire. Pour plus de détails et précautions, veuillez vous référer au document correspondant. Si les périphériques source et cible sont des processeurs, torch.from_numpy et torch.as_tensor ne copieront pas les données. Si les données source sont un tableau Numpy, utilisez torch.from_numpy est plus rapide. Si les données source sont un tenseur avec le même type de données et le même type de périphérique, torch.as_tensor peut éviter de copier les données, qui peuvent être une liste, un tuple ou un tenseur de Python. - Utilisez la transmission non bloquante, c'est-à-dire définir
non_blocking=True . Cela tente la conversion asynchrone dans la mesure du possible, par exemple, la conversion d'un tenseur de processeur dans la mémoire de verrouillage de la page dans un tenseur CUDA.
Optimisation de l'optimiseur
- Stockez les paramètres du modèle dans un morceau de mémoire continu, réduisant ainsi le temps d'
optimizer.step() .-
contiguous_pytorch_params
- Utilisation de blocs de construction fusionnés à Apex
Conception du modèle
CNN
- Shufflenetv2, papier.
- Les canaux d'entrée et de sortie de la couche de convolution sont cohérents: lorsque le nombre de canaux de fonctionnalité d'entrée et de sortie de la couche de convolution est égal, le Mac (temps de consommation d'accès à la mémoire, l'abréviation
memory access cost est MAC ) est le plus petit et la vitesse du modèle est la plus rapide à ce moment - Réduire le regroupement convolutionnel: trop d'opérations de groupe augmenteront le Mac, ce qui ralentira le modèle
- Réduire les branches du modèle: moins les branches du modèle sont moins élevées, plus le modèle est rapide
- Réduire les opérations
element-wise : la consommation temporelle apportée par les opérations element-wise est beaucoup plus grande que les valeurs reflétées dans les flops, de sorte que les opérations element-wise doivent être minimisées autant que possible. depthwise convolution a également les caractéristiques des basses flops faibles et du Mac élevé.
Transformateur de vision
- TRT-VIT: Transformateur de vision orienté tensorrt, article, interprétation.
- au niveau de la scène: le bloc transformateur convient aux stades ultérieurs du modèle, ce qui maximise le compromis entre l'efficacité et les performances.
- au niveau de la scène: le modèle de conception de la scène avec de peu profonde d'abord, puis profond peut améliorer les performances.
- Niveau de bloc: un bloc hybride de transformateur et d'étranglement est plus efficace qu'un transformateur séparé.
- Niveau de bloc: le modèle global puis local de conception de blocs aide à compenser les problèmes de performance.
Idées générales
- Réduire la complexité: par exemple, la coupe du modèle et l'élagage, réduisez les couches de modèle et l'échelle des paramètres
- Modifier la structure du modèle: par exemple, la distillation du modèle et obtenir de petits modèles par la méthode de distillation de connaissances
Accélérer le raisonnement
Demi-précision et pondération
Utilisez une représentation à faible précision ( FP16 ou même INT8 , réseau binaire et réseau à trois valeurs) pour remplacer la représentation de la précision d'origine ( FP32 ).
-
TensorRT est un moteur d'inférence du réseau neuronal proposé par NVIDIA, qui prend en charge la quantification post-entraînement à 8 bits. Il utilise un algorithme de quantification du modèle basé sur l'entropie pour minimiser le degré de différence entre les deux distributions. - Pytorch1.3 a déjà pris en charge la fonction de quantification, basée sur la mise en œuvre du QNNPACK, et prend en charge la quantification post-formation, la quantification dynamique et la formation de perception de quantification et d'autres technologies.
- De plus,
Distiller est un outil d'optimisation de modèle open source basé sur Pytorch et prend naturellement une technologie quantitative dans le pytorch. -
NNI de Microsoft intègre une variété d'algorithmes de formation de perception quantitative et prend en charge plusieurs frameworks open source tels que PyTorch/TensorFlow/MXNet/Caffe2
Pour plus de détails, veuillez vous référer à trois IA: [discours divers] Quels sont les outils open source disponibles pour la quantification actuelle du modèle?
Fusion opérationnelle
- Modèles de raisonnement d'accélération Compétences: fusion de couches BN et Conv - Articles de Xiaoxiaojiang - Zhihu
- La convergence de la couche Conv et de la couche BN dans l'étape d'inférence du réseau - Article d'Autocyz - Zhihu
- Pytorch lui-même offre des fonctionnalités similaires
Rediffusion
- Repvgg
- Repvgg | Laissez votre convnet jusqu'à la fin, un réseau simple dépasse 80% TOP1 pour la première fois
Analyse temporelle
- Python est livré avec plusieurs
profile d'analyse des performances, cProfile et hotshot . Les méthodes d'utilisation sont fondamentalement les mêmes. Ce n'est rien de plus que si le module est pur python ou écrit en C. - Pytorch Profiler est un outil qui collecte des mesures de performance pendant la formation et l'inférence. L'API du gestionnaire de contexte de Profiler peut être utilisée pour mieux comprendre quel opérateur de modèle est le plus cher, vérifier sa forme d'entrée et empiler les enregistrements, étudier l'activité du noyau des appareils et visualiser les enregistrements d'exécution.
Recommandation de projet
- Implémentez la compression du modèle basé sur Pytorch:
- Quantification: 8/4/2 bits (dorefa), valeur à trois valeurs / binaire (twn / bnn / xnor-net).
- Élagage: élagage normal, régulier et canal pour les structures convolutionnelles groupées.
- Structure convolutionnelle groupée.
- Fusion BN pour la quantification binaire des caractéristiques.
Lecture prolongée
- Le chargement des données de Pytorch DatalOader prend la plupart du temps. Comment le résolvez-vous? - Zhihu
- Lorsque vous utilisez Pytorch, il y a trop de données de formation de formation pour atteindre des dizaines de millions, et que dois-je faire si le dataloader se charge très lentement? - Zhihu
- Quels sont les pièges / bogues à Pytorch? - Zhihu
- Optimisation du code de formation Pytorch
- 26 secondes Formation de GPU Single CIFAR10, Jeff Dean aime également les compétences d'optimisation de l'apprentissage en profondeur - Articles au cœur des machines - Zhihu
- Après avoir entraîné quelques nouvelles fonctionnalités sur le modèle en ligne, pourquoi le temps de prédiction de TensorFlow sert-il plus de 20 fois plus lent que l'original? - Réponse de Tzesing - Zhihu
- Compression du modèle d'apprentissage en profondeur
- Aujourd'hui, votre modèle a-t-il accéléré? Voici 5 méthodes pour votre référence (avec analyse de code)
- Résumé des pièges communs à Pytorch - Articles de Yu Zhenbo - Zhihu
- Guide Pytorch SpeedUp - Articles de Yunmeng - Zhihu
- Optimiser la vitesse et l'efficacité de la mémoire de Pytorch (2022)
Pytorch enregistre la mémoire vidéo
Document original: https://www.yuque.com/lart/ugkv9f/nvffyf
Collecté à partir de: Quels sont les conseils pour enregistrer la mémoire (mémoire vidéo) dans Pytorch? - Zhihu https://www.zhihu.com/question/274635237
Utiliser en place
- Essayez d'activer les opérations qui prennent
inplace par défaut. Par exemple, relu peut utiliser inplace=True . -
batchnorm et certaines fonctions d'activation spécifiques peuvent être emballées dans inplace_abn .
Fonction de perte
La suppression de la perte à la fin de chaque boucle peut enregistrer très peu de mémoire vidéo, mais c'est mieux que rien. Tensor à la variable et à la mémoire libérant les meilleures pratiques
Précision de mélange
Il peut économiser une certaine quantité de mémoire vidéo et accélérer, mais faites attention aux opérations dangereuses telles que la moyenne et la somme.
- Introduction à la formation de précision mixte:
- Tutoriel de formation de précision mixte de peu profond à profond
- Support de précision mixte fourni par
NVIDIA/Apex .- Artefact incontournable pytorch | Fast-Free: Accélération de précision hybride basée sur Apex
- Installation pytorch d'Apex Solutions de maladie difficile et diverses - Articles de Chen Hanke - Zhihu
- Pytorch1.6 commence à fournir
torch.cuda.amp pour soutenir une précision mixte.
Gérer les opérations qui ne nécessitent pas de rétro-dorsion
- Pour les phases vers l'avant qui ne nécessitent pas de rétro-propagation, telles que les périodes de vérification et d'inférence, utilisez
torch.no_grad pour envelopper le code.- Notez que
model.eval() n'est pas égal à torch.no_grad() , veuillez consulter la discussion suivante: 'Model.eval ()' vs 'avec torch.no_grad ()'
- Définissez
requires_grad des variables qui n'ont pas besoin de calculer le gradient sur False , afin que la variable ne participe pas à la propagation arrière du gradient pour réduire l'utilisation de la mémoire des gradients inutiles. - Retirez le chemin de gradient qui n'a pas besoin d'être calculé:
- STOCHASTIC STOCKPROPAGATION: Une stratégie efficace de la mémoire pour la formation des modèles vidéo, l'interprétation peut être vue:
- https://www.yuque.com/lart/papers/xu5t00
- https://blog.csdn.net/p_lart/article/details/124978961
Nettoyage de la mémoire vidéo
-
torch.cuda.empty_cache() est une version avancée de del . L'utilisation de nvidia-smi constatera que la mémoire vidéo a des changements évidents. Cependant, l'utilisation maximale de la mémoire vidéo pendant la formation ne semble pas changer. Vous pouvez essayer: comment pouvons-nous libérer le cache de mémoire GPU? - Vous pouvez utiliser
del pour supprimer les variables intermédiaires inutiles ou utiliser la forme de replacing variables pour réduire l'occupation.
Accumulation de gradient
Divisez un batchsize=64 en deux lots de 32, et après deux transférés, en arrière une fois. Mais cela affectera batchnorm et d'autres couches liées à batchsize .
Dans la documentation de Pytorch, un exemple d'utilisation de l'accumulation de gradient et de la précision de mélange est mentionné.
Utiliser la technologie d'accumulation de gradient pour accélérer la formation distribuée, qui peut être utilisée pour se référer à: [original] [Deep] [Pytorch] DDP Series 3: Practical and Skills - 996 Articles de The Golden Generation - Zhihu
Poignage de contrôle du gradient
torch.utils.checkpoint est fourni à Pytorch. Ceci est réalisé en réexécutant la propagation vers l'avant à chaque emplacement de point de contrôle pendant la rétro-propagation.
La formation en papier NETS profondes avec le coût de la mémoire sous-linéaire est basée sur la technologie de point de contrôle de gradient pour réduire la mémoire vidéo de O (n) à O (SQRT (n)). Pour les modèles plus profonds, plus cette méthode économise de la mémoire et ne ralentit pas considérablement.
- Analyse du mécanisme de point de contrôle de Pytorch
- torch.utils.checkpoint introduction et facile à utiliser
- Une implémentation Pytorch du coût de la mémoire sous-linéaire, référencée de: Quels sont les conseils pour enregistrer la mémoire (mémoire vidéo) dans Pytorch? - Réponse de Lyken - Zhihu
Outils connexes
- Ces codes peuvent vous aider à détecter votre mémoire GPU pendant la formation avec Pytorch. https://github.com/oldpan/pytorch-memory-utils
- Juste moins que Nvidia-SMI? https://github.com/wookayin/gpustat
Références
- Quels sont les conseils pour enregistrer la mémoire (mémoire vidéo) dans Pytorch? - Réponse de Zheng Zhedong - Zhihu
- Une brève discussion sur l'apprentissage en profondeur: comment calculer l'empreinte mémoire des modèles et des variables intermédiaires
- Comment utiliser finement la mémoire vidéo à Pytorch
- Quels sont les conseils pour enregistrer la mémoire vidéo à Pytorch? - Réponse de Chen Hanke - Zhihu
- Analyse du mécanisme de mémoire vidéo Pytorch - Article de Connolly - Zhihu
Autres conseils
Reproduire
Vous pouvez suivre les chapitres pertinents du document.
Opération déterministe obligatoire
Évitez d'utiliser des algorithmes non déterministes.
Dans Pytorch, torch.use_deterministic_algorithms() peut forcer l'utilisation d'algorithmes déterministes au lieu d'algorithmes non déterministes, et une erreur est lancée si l'opération est connue pour être non déterministe (et aucune alternative déterministe).
Définir les graines de numéro aléatoire
def seed_torch ( seed = 1029 ):
random . seed ( seed )
os . environ [ 'PYTHONHASHSEED' ] = str ( seed )
np . random . seed ( seed )
torch . manual_seed ( seed )
torch . cuda . manual_seed ( seed )
torch . cuda . manual_seed_all ( seed ) # if you are using multi-GPU.
torch . backends . cudnn . benchmark = False
torch . backends . cudnn . deterministic = True
seed_torch () Référence à partir de https://www.zdaiot.com/mlframeworks/pytorch/pytorch%E9%9A%8F%E6%9C%BA%E7%A7%8D%E5%AD%90/
Bogue cachée dans DatalOader avant Pytorch Version 1.9
Les détails spécifiques montrent que 95% des personnes font toujours des erreurs de pytorch - Articles de sérendipité - Zhihu
Pour les solutions, veuillez vous référer à la documentation:
def seed_worker ( worker_id ):
worker_seed = torch . initial_seed () % 2 ** 32
numpy . random . seed ( worker_seed )
random . seed ( worker_seed )
DataLoader (..., worker_init_fn = seed_worker )