* Depuis août 2021, le code n'est plus maintenu. Il est conservé ici sous forme d'archives pour les personnes qui souhaitent continuer à l'utiliser.
? 1T ou casser mes mecs ?
Une implémentation de modèles parallèles de modèle et de données de type GPT3 à l'aide de la bibliothèque mesh-tensorflow.
Si vous êtes juste ici pour jouer avec nos modèles pré-entraînés, nous vous recommandons fortement d'essayer l'intégration de HuggingFace Transformer.
La formation et l'inférence sont officiellement prises en charge sur TPU et devraient également fonctionner sur GPU. Ce référentiel sera (en grande partie) archivé au fur et à mesure que nous nous concentrerons sur notre référentiel spécifique au GPU, GPT-NeoX.
En plus des fonctionnalités offertes par GPT-3, nous proposons également les éléments suivants :
NB, bien que neo puisse techniquement exécuter une étape de formation à plus de 200 milliards de paramètres, il est très inefficace à ces échelles. Ceci, ainsi que le fait que de nombreux GPU soient devenus disponibles, entre autres choses, nous ont incité à déplacer le développement vers GPT-NeoX.
Mise à jour du 21/03/2021 :
Nous sommes fiers de lancer deux modèles GPT-Neo pré-entraînés sur The Pile, les poids et les configurations peuvent être téléchargés gratuitement depuis the-eye.eu.
1.3B : https://mystic.the-eye.eu/public/AI/gptneo-release/GPT3_XL/
2.7B : https://mystic.the-eye.eu/public/AI/gptneo-release/GPT3_2-7B/
Pour plus d'informations sur la façon de les configurer, consultez le bloc-notes Colab ou lisez le reste du fichier Lisez-moi.
Modèle et taille | Pile BPB | Pile PPL | Wikitexte PPL | Lambada PPL | Lambada Acc | Winogrande | Hellaswag |
---|---|---|---|---|---|---|---|
GPT-Neo 125M | ----- | ----- | 32.285 | 30.266 | 37,36% | 50,43% | 28,67% |
GPT-3 125M | ----- | ----- | ----- | 18.6 | 42,7% | 52,0% | 33,7% |
GPT-Néo 350M | ----- | ----- | 22.5657 | 13.876 | 47,27% | 51,14% | 32,16% |
GPT-3 350M | ----- | ----- | ----- | 9.09 | 54,3% | 52,1% | 43,6% |
GPT-3 Ada | 0,9631 | ----- | ----- | 9.954 | 51,60% | 52,90% | 35,93% |
GPT-Neo 1.3B | 0,7527 | 6.159 | 13h10 | 7.498 | 57,23% | 55,01% | 38,66% |
GPT-3 1.3B | ----- | ----- | ----- | 5.44 | 63,6% | 58,7% | 54,7% |
GPT-2 1,5B | 1,0468 | ----- | 17h48 | 10.634 | 51,21% | 59,40% | 40,03% |
GPT-Neo 2.7B | 0,7165 | 5,646 | 11h39 | 5.626 | 62,22% | 56,50% | 42,73% |
GPT-3 2.7B | ----- | ----- | ----- | 4,60 | 67,1% | 62,3% | 62,8% |
Modèle et taille | MathQA | PubMedQA | Piqa |
---|---|---|---|
GPT-Neo 125M | 22,78% | 55,10% | 63,06% |
GPT-3 125M | ----- | ----- | 64,6% |
GPT-Néo 350M | 23,45% | 53,80% | 65,07% |
GPT-3 350M | ----- | ----- | 70,2% |
GPT-3 Ada | 24,29% | 52,80% | 68,88% |
GPT-Neo 1.3B | 24,05% | 54,40% | 71,11% |
GPT-3 1.3B | ----- | ----- | 75,1% |
GPT-2 1,5B | 23,64% | 58,33% | 70,78% |
GPT-Neo 2.7B | 24,72% | 57,54% | 72,14% |
GPT-3 2.7B | ----- | ----- | 75,6% |
Remarque : Toutes les évaluations ont été effectuées à l’aide de notre harnais d’évaluation. Certains résultats pour GPT-2 et GPT-3 ne correspondent pas aux valeurs rapportées dans les articles respectifs. Nous étudions actuellement pourquoi et apprécierions grandement vos commentaires et des tests supplémentaires sur notre harnais d'évaluation.
git clone https://github.com/EleutherAI/GPTNeo
cd GPTNeo
pip3 install -r requirements.txt
Inscrivez-vous à Google Cloud Platform et créez un bucket de stockage.
Créez votre VM via un shell Google ( https://ssh.cloud.google.com/
) avec ctpu up --vm-only
afin qu'elle puisse se connecter à votre bucket Google et à vos TPU et installer les exigences avec pip (voir ci-dessus) .
Google Colab fournit gratuitement des tpu-v8, ce qui devrait suffire pour affiner nos modèles jusqu'aux tailles GPT3XL (paramètre 1,5B). Cliquez pour parcourir notre exemple de notebook Colab.
Pour des instructions plus détaillées, parcourez notre guide de formation ci-dessous.
Vous pouvez également choisir d’entraîner GPTNeo localement sur vos GPU. Pour ce faire, vous pouvez omettre les étapes de configuration du cloud Google ci-dessus et cloner le dépôt localement. Parcourez le guide de formation ci-dessous, puis lors de l'exécution de main.py, il vous suffit d'omettre l'indicateur tpu
et de transmettre les identifiants GPU à la place.
Remarque : Certains utilisateurs ont signalé avoir des difficultés à faire reconnaître leurs GPU par MTF. Voir ici pour plus de détails et d'instructions sur la façon de résoudre ce problème.
Une fois que vous disposez d'un modèle entraîné ou que vous avez téléchargé l'un de nos modèles pré-entraînés, générer du texte est aussi simple que d'exécuter le script main.py avec l'indicateur --predict
activé. Vous pouvez transmettre un chemin vers votre fichier txt d'invite avec l'indicateur --prompt
, comme ceci :
python3 main.py --predict --prompt < example_prompt.txt > --tpu < tpu_name > --model < config_name >
ou, si vous utilisez des GPU :
python3 main.py --predict --prompt < example_prompt.txt > --gpu_ids < device:GPU:0 device:GPU: 1> --model < config_name >
Nous vous recommandons d'utiliser le tokenizer GPT2 pré-entraîné de Huggingface avec notre dépôt (instructions fournies ci-dessous), mais si vous souhaitez entraîner un modèle avec une taille de vocabulaire différente, nous proposons des fonctionnalités pour entraîner votre propre tokenizer comme suit :
python data/train_tokenizer.py
--base_dir ./path/to/your/txt/files
--output_dir ./output/path
--file_type txt
--vocab_size 50257
# if it succeeded, you should see the message
# 'tokenizer saved at ./output/path/byte-level-bpe.tokenizer.json'
Si vous souhaitez simplement tester l'entraînement, vous pouvez ignorer cette étape et télécharger des données factices comme ceci :
wget https://storage.googleapis.com/connors-datasets/bundestag/bundestag_0.tfrecords
Copiez ensuite les données dans votre bucket ou, si vous utilisez des GPU, dans un répertoire local :
gsutil cp bundestag_0.tfrecords gs://<your bucket>/
Si vous utilisez vos propres données pour vous entraîner, vous pouvez utiliser le script data/create_tfrecords.py
pour encoder vos données texte dans tfrecords.
Vos données doivent être soit sous la forme de nombreux fichiers .txt normaux (un document par fichier), soit dans n'importe quel format pris en charge par lm_dataformat.
Vous pouvez exécuter le script sans paramètres pour afficher l'aide sur toutes les options.
En mode document Chaque exemple dans les tfrecords est un document (de taille variable). Ceci doit être utilisé avec les modes d'échantillonnage documents_fixed
et documents_random
(pour plus de détails, voir la section de référence des paramètres). Le mode Document est le mode par défaut.
La commande ci-dessous tokenisera tous les fichiers dans des formats acceptables dans base_dir à l'aide de gpt2 tokenizer et les enregistrera dans output_dir.
python3 create_tfrecords.py --mode documents --input_dir <base> --name <name> --output_dir <output> --use_gpt2_tokenizer --minimum_size <min>
input_dir
: Définit le dossier où se trouvent vos données. Le script encodera tous les fichiers présents dans ce dossier.name
: Le nom des fichiers de sortie sera name_i.tfrecords
où i est le numéro du fichier.output_dir
: Où enregistrer les tfrecordsuse_gpt2_tokenizer
: s'il faut utiliser le tokenizer HuggingFace GPT2 pré-entraîné, auquel cas le séparateur sera défini sur [50256].encoder_path
: si vous n'utilisez pas le tokenizer gpt2 pré-entraîné, utilisez cet indicateur pour fournir un chemin vers votre tokenizer json généré.separator
: Écrit sous forme de liste, le(s) jeton(s) séparateur(s) à insérer entre les documents (par exemple "[0]"). Cela dépendra de votre encodeur.minimum_size
: La taille minimale (en jetons) qu'un document doit avoir, sinon il est supprimé. C'est ce qui déterminera plus tard votre paramètre stitch
: stitch * minimum_size
doit toujours être supérieur ou égal n_ctx
(Pour plus de détails voir la section de référence des paramètres). Pour utiliser un ensemble de données dans un modèle, vous devez d'abord enregistrer cet ensemble de données dans le dossier ./configs/dataset_configs
. Choisissez d’abord un nom de fichier avec une extension .json
. Ce nom de fichier servira d’identification de l’ensemble de données. La configuration doit être remplie de la manière suivante.
Si vous disposez d'un ensemble de données encodé à l'aide du tokenizer gpt2 pré-entraîné, vous pouvez le spécifier comme ceci :
{
"n_vocab" : 50257 ,
"path" : " gs://neo-datasets/openwebtext-documents/openwebtext_*.tfrecords " ,
"eval_path" : " gs://neo-datasets/openwebtext-documents/openwebtext_*.tfrecords " ,
"tokenizer_is_pretrained" : true ,
"tokenizer_path" : " gpt2 "
}
ou si vous avez formé un tokenizer personnalisé, comme ceci :
{
"n_vocab" : 32768 ,
"path" : " ./path/to/your/*.tfrecords " ,
"eval_path" : " ./path/to/your/eval/*.tfrecords " ,
"tokenizer_path" : " ./path/to/your/byte-level-bpe.tokenizer.json "
}
Enfin, dans la configuration de votre modèle, ajoutez le nom de fichier que vous avez créé ci-dessus au tableau datasets
.
Le <dataset id>
sera le nom de fichier, à l'exclusion du .json
, que vous avez créé ci-dessus
"datasets": [[<dataset id>, <stitch>, <datatype>, <weight>]] # datasets key defines at run time how each dataset is processed for training
Une fois vos ensembles de données configurés, recherchez une configuration appropriée dans /configs
.
Ici, nous utilisons un modèle de taille GPT3-XL comme exemple, mais il y en a beaucoup d'autres dans ./configs
, qui ont tous de courts résumés dans la section Configurations disponibles.
Tout ce que vous avez à faire est de modifier l'ID de l'ensemble de données comme décrit ci-dessus et de modifier model_path
(où les journaux et les points de contrôle seront enregistrés) pour pointer vers un compartiment cloud auquel vous avez accès en écriture (ou un chemin local, si vous utilisez des GPU).
{
"n_head" : 32 ,
"n_vocab" : 50257 ,
"embed_dropout" : 0.1 ,
"lr" : 0.0002 ,
"lr_decay" : " cosine " ,
"warmup_steps" : 3000 ,
"beta1" : 0.9 ,
"beta2" : 0.95 ,
"epsilon" : 1e-8 ,
"opt_name" : " adam " ,
"weight_decay" : 0.1 ,
"train_batch_size" : 512 ,
"attn_dropout" : 0.1 ,
"train_steps" : 286150 ,
"eval_steps" : 0 ,
"predict_steps" : 1 ,
"res_dropout" : 0.1 ,
"eval_batch_size" : 128 ,
"predict_batch_size" : 1 ,
"iterations" : 2500 ,
"n_embd" : 2048 ,
"datasets" : [[ " your_dataset_name " , 25 , " documents_random " , 1.0 ]],
"model_path" : " gs://neo-models/GPT3_XL " ,
"n_ctx" : 2048 ,
"n_layer" : 24 ,
"scale_by_depth" : true ,
"scale_by_in" : false ,
"attention_types" : [[[ " global " ], 24 ]],
"mesh_shape" : " x:128,y:2 " ,
"layout" : " batch:x,memory_length:y,embd:y " ,
"activation_function" : " gelu " ,
"recompute_grad" : true ,
"gradient_clipping" : 1.0 ,
"tokens_per_mb_per_replica" : 2048
}
python3 main.py --model <your_config_name> --steps_per_checkpoint <n> --tpu <tpu-name>
tpu
: Nom du TPU à utiliser.steps_per_checkpoint
: La fréquence en étapes à laquelle enregistrer les points de contrôle.--auto_layout
et --auto_layout_and_mesh_shape
(Facultatif) : désactivez l'entraînement et générez automatiquement une layout
efficace en mémoire (et mesh_shape
)gpu_ids
: si vous vous entraînez à l'aide de GPU, omettez l'indicateur tpu
et transmettez les identifiants de vos GPU. Dans l'exemple ci-dessous, nous nous entraînons sur 3 GPU, en précisant leurs identifiants d'appareils délimités par des espaces : python3 main.py --model <your_config_name> --steps_per_checkpoint <n> --gpu_ids <device:GPU:0 device:GPU:1>
Nous avons plusieurs tailles de modèles disponibles, mais certaines de nos configurations nécessitent de grands TPU et devront être peaufinées pour fonctionner sur des machines plus petites ou des GPU. Vous trouverez ci-dessous un petit guide de chaque modèle dans le répertoire configs :
FAIRE
Sacred aide à suivre les expériences et est beaucoup plus agréable à travailler que Tensorboard.
Pour configurer :
Installer Docker et Docker-compose
Exécutez docker-compose up
Pour utiliser :
Assurez-vous que model_dir ne contient aucun journal de métriques (il déclenche les éléments métriques pour Tensorboard, ce qui suppose qu'il s'agit d'une continuation de l'exécution existante). Vous pouvez utiliser gsutil rm -r ...
pour supprimer le répertoire du modèle
Exécutez python3 run_experiment.py --tpu sometpuhere --model someconfig.json
Les options sont les mêmes que main.py
.
Vous pouvez accéder à http://server_ip_goes_here:8081/ pour voir la présentation d'Omniboard. Si vous préférez voir un tensorboard, le script en fait également tourner un et lui attribue automatiquement un port. Le script doit imprimer le port du tensorboard en haut du journal.
Si jamais vous êtes confus par l'ensemble de données d'un fichier de configuration particulier, vous pouvez facilement vérifier les identifiants de jeton minimum et maximum avec une seule commande. Ceci est utile pour s'assurer que la taille du vocabulaire du modèle est au moins aussi grande que l'identifiant maximum du jeton. Tensorflow ne générera pas d'erreur si vous essayez de rassembler sur une matrice avec des indices hors limites, vous devez donc vous assurer que la taille de votre vocabulaire est suffisamment grande.
python main --model {config_name} --check_dataset
En plus de pouvoir former de gros GPT, ce référentiel vous permet également de faire facilement de la modélisation en langage masqué (BERT, RoBERTa). Pour ce faire, vous devez suivre deux étapes supplémentaires.
Lors de la tokenisation de votre ensemble de données, vous devez réserver un identifiant spécial pour le jeton [mask]
.
Dans les configs, vous devrez définir deux champs supplémentaires
"mlm_training" : true , # must be set to true
"mlm_mask_id" : < mask id > # the mask id that you reserved from above
C'est tout ce dont vous avez besoin pour former un modèle avec l'objectif MLM, adapté à tout type de données que vous avez correctement encodées. Si vous souhaitez modifier les autres hyperparamètres associés, veuillez continuer à lire.
"mlm_cls_token_id" : < cls token id > , # auto append specified CLS token id on the left
"mlm_mask_prob" : 0.15 , # the probability of masking a token, defaults to 15%
"mlm_same_token_prob" : 0.10 , # probability of keeping the token the same, defaults to 10%
"mlm_random_token_prob" : 0.10 , # probability of tokens that are replaced with random tokens, 10% was recommended by the BERT paper
"mlm_mask_ignore_ids" : [ < cls token > , < sep token > ] # ignore masking other special tokens, if any
Choisissez une configuration valide dans /configs
et modifiez les paramètres si nécessaire :
n_heads
: Le nombre de têtes d'attention.n_embd
: Taille des calques cachés, doit être divisible par n_heads
.n_vocab
: Taille du vocabulaire.embed_dropout
, res_dropout
, attn_dropout
: probabilité d'abandon pour l'incorporation/résidus/attention de motslr
: Taux d'apprentissagewarmup_steps
: Nombre d'étapes avant que le taux d'apprentissage complet soit atteint (rampe linéaire de 0
à lr
).lr_decay
: cosine
ou linear
.opt_name
: adam
ou adafactor
.beta1
, beta2
et epsilon
: paramètres de l'optimiseur adam
.beta1
, ada_epsilon1
et ada_epsilon2
: paramètres de l'optimiseur adafactor
.weight_decay
: paramètre de dégradation du poids, s'il n'est pas présent, aucune dégradation du poids n'est utilisée (le correctif de dégradation du poids pour Adam est utilisé) (par défaut : 0,01) (facultatif).train_batch_size
: Taille du lot pendant l'entraînement.train_steps
: Nombre d'étapes de formation (lots), défini à environ ~ 1 époque pour l'instant (nombre total de jetons dans votre ensemble de données / nombre de jetons par lot (= train_batch_size
/ n_ctx
)).eval_steps
: Nombre d'étapes à exécuter pour chaque évaluation. Mis à 0
pour aucune évaluation. c'est-à-dire qu'après chaque point de contrôle, le modèle est testé pour eval_steps
iterations
: le nombre d'étapes mises en file d'attente vers le TPU doit être inférieur à steps_per_checkpoint
. (par défaut : 500)datasets
: Liste des jeux de données tfrecords à utiliser. Chaque ensemble de données est une liste avec les paramètres suivants : [train glob , eval glob, stitch, sampling_mode, weight]
. Ainsi par exemple pour un seul ensemble de données (notez la double liste) : [["bundestag_*.tfrecords", "", 10, "random_sample", 1.0]]
dataset_id
: Le nom d'un fichier de configuration d'ensemble de données dans ./configs/dataset_configs
stitch
: Si sampling_mode
random_sample
est utilisé, le pipeline d'entrée échantillonne cette quantité de textes en un seul à partir duquel échantillonner. Vous devez sélectionner le point de sorte que stitch * minimum_document_length >= n_ctx
sampling_mode
: chunks
(les tfrecords sont prétraités à la bonne longueur et sont lus séquentiellement) ou documents_random
(le nombre de stitch
de documents est concaténé puis un morceau n_ctx
est sous-échantillonné de manière aléatoire)weights
: quel poids relatif cet ensemble de données devrait avoir par rapport aux autresmodel
: Quel modèle entraîner. Actuellement, seul GPT
est pris en charge, et la valeur par défaut est celle-ci s'il n'est pas présent.model_path
: emplacement du compartiment de stockage Google (ou chemin local, si vous utilisez des GPU) pour enregistrer les points de contrôle et les journaux du modèle.n_ctx
: Taille de la fenêtre contextuelle. La valeur par défaut est 2048n_layer
: Nombre de couches (blocs) dans le modèle.scale_by_depth
: Si vrai, l'initialisation du poids des couches est mise à l'échelle en fonction de leur profondeur comme dans l'article GPT2.scale_by_in
: Si vrai, l'initialisation du poids des couches est mise à l'échelle en fonction de leur nombre d'entrées comme dans l'article GPT2.mesh_shape
: Un maillage est un tableau à n dimensions de processeurs avec des dimensions nommées utilisé pour le parallélisme dans la bibliothèque mesh-tensorflow. Chaque Tensor est réparti uniformément sur les dimensions du maillage en fonction de la disposition (voir ci-dessous). Le 'mesh_shape' est la forme de ce tableau et doit être égal au nombre de processeurs. par exemple, pour un TPU v3-128 "mesh_shape": "x:16,y:8".layout
: Un Tensor est disposé sur son maillage avec une tranche sur chaque processeur. Une « mise en page » de Tensor est une carte partielle injective spécifiant quelles dimensions du tenseur sont (également) réparties sur quelles dimensions du maillage. Aucune dimension d'un tenseur ne peut être divisée sur deux dimensions de son maillage et aucune dimension d'un tenseur ne peut être divisée sur la même dimension de son maillage. L'utilisateur définit un ensemble global de règles de mise en page sous la forme de paires (tenseur-dimension-nom, maillage-dimension-nom). Une dimension d'un tenseur est divisée sur une dimension de son maillage s'il existe une règle de correspondance, par exemple (pour l'exemple ci-dessus mesh_shape : "layout": "batch: x, heads: y"activation_function
: selu
(auto-normalisant) ou gelu
(utilisé par OA), fonction d'activation utilisée dans les passes feed-forward. (par défaut : gelu)attention_types
: le type d'attention pour chaque couche dans une liste au format suivant [[["attention_type"], n_layers]]. par exemple pour un réseau à 12 couches [[["global"], 12]] ou [[["local"], 10], [["global"], 2]].linear
, global
, local
ou none
. Nous avons trouvé un mélange 50/50 de global
et linear
qui fonctionne bien. none
vous permet de créer des couches à action directe uniquement pour des modèles de transformateur PAR plus efficaces.precision
: float32
ou bfloat16
.tokens_per_mb_per_replica
: Si ce n'est pas Aucun, divisera le lot en microlots plus petits contenant des jetons tokens_per_mb_per_replica
pour éviter les MOO. Les dégradés sont accumulés localement et réduits une fois. IMPORTANT : Mo fait référence ici à un minibatch et non à un mégaoctet.Mélange d'experts
moe_layers
: Une liste de numéros de calque sur laquelle ajouter un mélange de calques experts. PAR EXEMPLE : [2,4,6,8,10,12]
. Nous avons découvert expérimentalement qu'une couche moe pour deux couches d'auto-attention fonctionne bien.moe_params
: un dictionnaire de kwargs supplémentaires à transmettre à la couche moe. PAR EXEMPLE {"moe_dropout_rate": 0.0 }
Fonctionnalités expérimentales
axial_pos_emb_
: si vrai, utilise [intégration positionnelle axiale](https://arxiv.org/abs/1912.12180.mlp_glu
: si vrai, utilise une variante d'unité linéaire fermée des couches de rétroaction.scalenorm
: Si vrai, utilise scalenorm au lieu de layernorm.rezero
: Si vrai, utilise rezero au lieu de layernorm.num_mem_kv
: ajoute la mémoire/les valeurs clés du document de grande attention. Param est un entier avec le nombre de valeurs mem/key souhaitées.macaron
: si vrai - utilise un transformateur macaron pour chaque bloc de calque. Si vous avez trouvé GPT-Neo utile dans votre travail, vous pouvez citer ce référentiel comme
@software{gpt-neo,
author = {Black, Sid and
Gao, Leo and
Wang, Phil and
Leahy, Connor and
Biderman, Stella},
title = {{GPT-Neo: Large Scale Autoregressive Language
Modeling with Mesh-Tensorflow}},
month = mar,
year = 2021,
note = {{If you use this software, please cite it using
these metadata.}},
publisher = {Zenodo},
version = {1.0},
doi = {10.5281/zenodo.5297715},
url = {https://doi.org/10.5281/zenodo.5297715}
}
Le numéro de version doit être remplacé par le numéro de version que vous utilisez et l'année correspond à la version open source du projet.
Si vous souhaitez spécifiquement citer les modèles GPT-Neo formés sur la Pile, nous apprécierions également de citer
@article{gao2020pile,
title={The Pile: An 800GB Dataset of Diverse Text for Language Modeling},
author={Gao, Leo and Biderman, Stella and Black, Sid and Golding, Laurence and Hoppe, Travis and Foster, Charles and Phang, Jason and He, Horace and Thite, Anish and Nabeshima, Noa and others},
journal={arXiv preprint arXiv:2101.00027},
year={2020}
}