File size: 7,356 Bytes
91feea3
4e0a704
91feea3
d5b15a3
60d30cc
91feea3
 
 
 
 
72b1673
ae63b0f
 
03f2529
 
 
 
3a0bedd
91feea3
50b8512
ada63db
50b8512
 
 
21357fc
50b8512
ada63db
 
 
 
 
 
 
 
 
 
 
 
 
 
 
50b8512
 
0e34887
 
181494a
0e34887
cc3b6f3
 
37c4d2f
115c7e5
ac9bcef
f3a3745
91feea3
cc37d8c
91feea3
50daa38
91feea3
50daa38
91feea3
013cf76
9f3da8d
c50213d
60d9a0b
 
181494a
72b1673
 
 
181494a
 
4b87cce
181494a
ae63b0f
 
 
 
9acbf52
b596828
ae63b0f
181494a
 
 
 
 
 
 
72b1673
 
 
 
 
 
 
 
1a07f51
72b1673
 
 
 
 
 
 
 
ba2d3ab
 
72b1673
618fdbd
7ddeab6
252f8d4
 
 
72b1673
 
d500f0f
77ee5c9
252f8d4
 
 
 
 
 
 
 
91fda76
 
a6ca5ee
72b1673
1a07f51
72b1673
95d0743
 
 
72b1673
 
 
7ddeab6
9f3da8d
ab50a43
95d0743
1a07f51
95d0743
a6ca5ee
252f8d4
dde4e83
95d0743
7f61353
d8a47fd
deb4c1f
 
 
 
 
dde4e83
f3a3745
 
 
 
 
03c2d80
f3a3745
 
 
 
 
 
 
3e7d36b
 
 
8047a4c
03c2d80
f3a3745
dde4e83
618fdbd
5e79674
91feea3
03c2d80
d8a47fd
 
37b019f
b70f00d
f1d9659
37b019f
03c2d80
0e34887
 
 
 
 
03c2d80
0589738
d90f136
3e7d36b
 
 
8bad0a0
3447965
91feea3
 
 
0e34887
72b1673
a4f2192
72b1673
 
831f0b2
72b1673
91feea3
ecd5b13
1d2196a
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
#!/usr/bin/env python
# -*- coding: utf-8 -*- 

import os 
from huggingface_hub import login
import gradio as gr
#from transformers import pipeline 
import torch
from utils import *
from presets import *
from transformers import Trainer, TrainingArguments
import numpy as np
import evaluate
import pandas as pd
import sklearn
from sklearn.model_selection import train_test_split
from sklearn.metrics import accuracy_score, recall_score, precision_score, f1_score


#####################################################
#Hilfsfunktionen für das Training
#####################################################
#Datensets in den Tokenizer schieben...
def tokenize_function(examples):
    return tokenizer(examples["text"])

#Funktion, die den gegebenen Text aus dem Datenset gruppiert
def group_texts(examples):
    # Concatenate all texts.
    concatenated_examples = {k: sum(examples[k], []) for k in examples.keys()}
    total_length = len(concatenated_examples[list(examples.keys())[0]])
    # We drop the small remainder, we could add padding if the model supported it instead of this drop, you can
    # customize this part to your needs.
    total_length = (total_length // block_size) * block_size
    # Split by chunks of max_len.
    result = {
        k: [t[i : i + block_size] for i in range(0, total_length, block_size)]
        for k, t in concatenated_examples.items()
    }
    result["labels"] = result["input_ids"].copy()
    return result    





###################################################################################
###################################################################################
#Access-Token (in Secrets)

#aus den Secrets importieren (siehe Setting zu diesem Space)
#login(token=os.environ["HF_ACCESS_TOKEN"])
     
#Modelle und Tokenizer

#Alternativ mit beliebigen Modellen:
#base_model = "project-baize/baize-v2-7b"  #load_8bit = False (in load_tokenizer_and_model)
#base_model = "TheBloke/airoboros-13B-HF"  #load_8bit = False (in load_tokenizer_and_model)
base_model = "EleutherAI/gpt-neo-1.3B"    #load_8bit = False (in load_tokenizer_and_model)
#base_model = "TheBloke/airoboros-13B-HF"   #load_8bit = True
tokenizer,model,device = load_tokenizer_and_model(base_model,  False)
#tokenizer.add_special_tokens({'pad_token': '[PAD]'}) #not necessary with fast Toekenizers like GPT2

dataset_neu = daten_laden("alexkueck/tis") 
#dataset_neu = daten_laden("EleutherAI/pile")

#############################################
#Vorbereiten für das Training der neuen Daten
#############################################

#alles zusammen auf das neue datenset anwenden - batched = True und 4 Prozesse, um die Berechnung zu beschleunigen. Die "text" - Spalte braucht man anschließend nicht mehr, daher weglassen.
tokenized_datasets = dataset_neu.map(tokenize_function, batched=True, num_proc=4, remove_columns=["id","text"])

#wenn man zum Trainieren erstmal nur einen kleinen Datensatz nehem möchte:
#small_train_dataset = tokenized_datasets["train"].shuffle(seed=42).select(range(1000))
#small_eval_dataset = tokenized_datasets["test"].shuffle(seed=42).select(range(1000))

print (tokenized_datasets["train"][4])


#den Text nun zusammenführen (concatenieren) und anschließend in kleine Häppchen aufteilen (block_size=128), die verarbeitet werden können
#das macht die map-Funktion und das Attribut batched = True
#man könnte das weglassen, wenn jeder Satz einzeln gegeben wurde in den Texten...
#eigentlich nimmt man als block_size die max. Länge in der das Model trainiert wurde -> könnte aber zu groß sein für den RAm der GPU , daher hier 128 gewählt
# block_size = tokenizer.model_max_length
block_size = 128

#nochmal die map-Funktion auf das bereits tokenisierte Datenset anwenden
#die bereits tokenisierten Datensatze ändern sich dadurch: die samples enthalten nun Mengen aus block_size Tokens
lm_datasets = tokenized_datasets.map(
    group_texts,
    batched=True,
    batch_size=1000,
    num_proc=4,
)
print ("lm datasets")
#die Daten wurden nun "gereinigt" und für das Model vorbereitet.
#z.B. anschauen mit: tokenizer.decode(lm_datasets["train"][1]["input_ids"])

####################################################
#Training
####################################################

#Training Args
batch_size = 2

training_args = TrainingArguments(
    output_dir="alexkueck/test-tis-1",
    overwrite_output_dir = 'True',
    per_device_train_batch_size=batch_size,  #batch_size = 2 for full training
    per_device_eval_batch_size=batch_size,
    evaluation_strategy = "epoch",  #oder steps
    learning_rate=2e-5,
    weight_decay=0.01,
    save_total_limit = 2,
    #predict_with_generate=True,
    #logging_steps=2,  # set to 1000 for full training
    #save_steps=16,    # set to 500 for full training
    #eval_steps=4,     # set to 8000 for full training
    #warmup_steps=1,   # set to 2000 for full training
    #max_steps=16,     # delete for full training
    # overwrite_output_dir=True,
    #save_total_limit=1,
    #fp16=True,
    save_strategy = "no",
    load_best_model_at_end=False,
    #push_to_hub=True,
)
print ("training args")
############################################
#def trainieren_neu(name):
#Trainer zusammenstellen
trainer = Trainer(
        model=model,
        args=training_args,
        train_dataset=lm_datasets["train"],
        eval_dataset=lm_datasets["test"],
        #tokenizer=tokenizer,
        #compute_metrics=compute_metrics,
)
print ("trainer")
#trainer ausführen
trainer.train()
#Wenn man vom letzten checkpoint aus weiter trainieren möchte: trainer.train(resume_from_checkpoint=True)
print("trained!!!!!")
#in den Hub laden
#trainer.push_to_hub("test-tis", use_auth_token=True)

##################
#Evaluate the new Model
print("Evaluate:")
trainer.evaluate()
print("Done Eval")

############################
#Test
############################
print("Test")
text = "Was ist Tis?"
'''
encoding = tokenizer(text, return_tensors="pt")
encoding = {k: v.to(trainer.model.device) for k,v in encoding.items()}

outputs = trainer.model(**encoding)
logits = outputs.logits
print(logits.shape)

#greedy_output = model.generate(input_ids, max_length=50)

print("Output:\n" )
#print(tokenizer.decode(outputs[0], skip_special_tokens=True))
'''

print("Save to Space")
#trainer.save_model("alexkueck/test-tis-1")
print("done")

'''
#####################################
#Push to Hub
print("push to hub")
login(token=os.environ["HF_WRITE_TOKEN"]) 
trainer.push_to_hub("test-tis-1")
print("done")
'''


##############################################
#Testen des fine-tuned Modells
print("Predict")
model_neu = "test-tis-1"
tokenizer_neu,model_neu, device_neu = load_tokenizer_and_model(model_neu, False)
antwort = predict(model_neu, tokenizer_neu, device_neu, "Was ist Tis?", [["Tis", ""]], top_p=5,
            temperature=0.8,
            max_length_tokens=1024,
            max_context_length_tokens=2048,)
print(antwort)
print("done Predict")

#######################################################################
#Darstellung mit Gradio
'''
with gr.Blocks() as demo:
    name = gr.Textbox(label="Model")
    output = gr.Textbox(label="Output Box")
    start_btn = gr.Button("Start")
    start_btn.click(fn=trainieren_neu, inputs=name, outputs=output, api_name="trainieren_neu")


demo.queue(default_enabled=True).launch(debug=True) 
'''