jahongirtech commited on
Commit
f0fc7d1
Β·
verified Β·
1 Parent(s): 983579c

Create model_trainer.py

Browse files
Files changed (1) hide show
  1. model_trainer.py +182 -0
model_trainer.py ADDED
@@ -0,0 +1,182 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import os
2
+ import torch
3
+ import torch.distributed as dist
4
+ import torch.multiprocessing as mp
5
+ import librosa
6
+ import soundfile as sf
7
+ from pathlib import Path
8
+
9
+ os.environ["CUDA_VISIBLE_DEVICES"] = "0,1"
10
+
11
+ # ─────────────────────────────────────────
12
+ # AUDIO PREPROCESSING
13
+ # ─────────────────────────────────────────
14
+ def preprocess_audio(dataset_path, target_sr=22050):
15
+ wavs_dir = os.path.join(dataset_path, "wavs")
16
+ wav_files = list(Path(wavs_dir).glob("*.wav"))
17
+ already_done = os.path.join(dataset_path, ".preprocessed")
18
+ if os.path.exists(already_done):
19
+ print("βœ… Audio allaqachon tayyor.")
20
+ return
21
+ print(f"πŸ”„ {len(wav_files)} ta wav qayta ishlanmoqda...")
22
+ for wav_path in wav_files:
23
+ audio, sr = librosa.load(str(wav_path), sr=target_sr, mono=True)
24
+ sf.write(str(wav_path), audio, target_sr)
25
+ open(already_done, "w").close()
26
+ print("βœ… Barcha wav mono + 22050 Hz ga o'tkazildi.")
27
+
28
+ dataset_path = "/content/drive/MyDrive/tts/dataset_final"
29
+ preprocess_audio(dataset_path)
30
+
31
+ # ─────────────────────────────────────────
32
+ # TRAIN FUNKSIYASI β€” har bir GPU uchun alohida ishga tushadi
33
+ # ─────────────────────────────────────────
34
+ def train(rank, world_size):
35
+ """rank=0 β†’ GPU0, rank=1 β†’ GPU1"""
36
+
37
+ # DDP ni ishga tushirish
38
+ os.environ["MASTER_ADDR"] = "localhost"
39
+ os.environ["MASTER_PORT"] = "12355"
40
+ dist.init_process_group("nccl", rank=rank, world_size=world_size)
41
+ torch.cuda.set_device(rank)
42
+
43
+ print(f"βœ… GPU {rank}/{world_size} ishga tushdi: {torch.cuda.get_device_name(rank)}")
44
+
45
+ from TTS.tts.configs.shared_configs import CharactersConfig, BaseDatasetConfig
46
+ from TTS.tts.configs.vits_config import VitsConfig
47
+ from TTS.tts.datasets import load_tts_samples
48
+ from TTS.tts.models.vits import Vits
49
+ from TTS.utils.audio import AudioProcessor
50
+ from TTS.tts.utils.text.tokenizer import TTSTokenizer
51
+ from trainer import Trainer, TrainerArgs
52
+
53
+ # ── CONFIG ──
54
+ config = VitsConfig(
55
+ run_name="Xurmo Media 20",
56
+ batch_size=16, # Har bir GPU uchun 16 β†’ jami 32
57
+ eval_batch_size=8,
58
+ num_loader_workers=2,
59
+ num_eval_loader_workers=2,
60
+ epochs=1000,
61
+ text_cleaner="multilingual_cleaners",
62
+ use_phonemes=False,
63
+ mixed_precision=True, # FP16 β€” T4 da 2x tezlik
64
+ run_eval=True,
65
+ save_step=1000,
66
+ save_n_checkpoints=3,
67
+ print_step=50,
68
+ output_path="/content/drive/MyDrive/tts/output",
69
+ characters=CharactersConfig(
70
+ characters="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyzO'o'G'g'ShshChch'0123456789",
71
+ punctuations="!,.? ",
72
+ pad="<PAD>",
73
+ eos="<EOS>",
74
+ bos="<BOS>",
75
+ blank="<BLNK>",
76
+ ),
77
+ )
78
+ config.audio.sample_rate = 22050
79
+ config.audio.do_trim_silence = True
80
+ config.audio.resample = False
81
+
82
+ # ── FORMATTER ──
83
+ def formatter(root_path, meta_file, **kwargs):
84
+ txt_file = os.path.join(root_path, meta_file)
85
+ items = []
86
+ with open(txt_file, "r", encoding="utf-8") as f:
87
+ for line in f:
88
+ line = line.strip()
89
+ if not line:
90
+ continue
91
+ cols = line.split("|")
92
+ if len(cols) < 2:
93
+ continue
94
+ wav_file = os.path.join(root_path, "wavs", cols[0].strip() + ".wav")
95
+ text = cols[1].strip()
96
+ # Typographic apostrof β†’ oddiy apostrof
97
+ text = text.replace("\u2018", "'").replace("\u2019", "'")
98
+ text = text.replace("\u02bc", "'").replace("\u0060", "'")
99
+ if not os.path.exists(wav_file):
100
+ continue
101
+ items.append({
102
+ "text": text,
103
+ "audio_file": wav_file,
104
+ "root_path": root_path,
105
+ "speaker_name": "xurmo media",
106
+ "language": "uz",
107
+ })
108
+ if rank == 0:
109
+ print(f"βœ… {len(items)} ta sample yuklandi.")
110
+ return items
111
+
112
+ # ── DATASET ──
113
+ dataset_config = BaseDatasetConfig(
114
+ dataset_name="uzbek_tts",
115
+ path=dataset_path,
116
+ meta_file_train="metadata.csv",
117
+ meta_file_val="",
118
+ language="uz",
119
+ )
120
+ train_samples, eval_samples = load_tts_samples(
121
+ [dataset_config],
122
+ eval_split=True,
123
+ eval_split_size=0.1,
124
+ formatter=formatter,
125
+ )
126
+
127
+ # ── MODEL ──
128
+ tokenizer, config = TTSTokenizer.init_from_config(config)
129
+ ap = AudioProcessor.init_from_config(config)
130
+ model = Vits(config, ap, tokenizer, speaker_manager=None)
131
+
132
+ # ── TRAINER β€” rank va world_size ni uzatamiz ──
133
+ trainer_args = TrainerArgs(
134
+ rank=rank,
135
+ group_id=f"group_{rank}",
136
+ use_ddp=True,
137
+ grad_accum_steps=1, # VITS GAN uchun majburiy =1
138
+ )
139
+
140
+ trainer = Trainer(
141
+ trainer_args,
142
+ config,
143
+ output_path="/kaggle/working/output",
144
+ model=model,
145
+ train_samples=train_samples,
146
+ eval_samples=eval_samples,
147
+ )
148
+
149
+ if rank == 0:
150
+ print(f"""
151
+ ╔══════════════════════════════════════╗
152
+ β•‘ πŸš€ Colab T4 O'QITISH β•‘
153
+ β•‘ Har GPU batch : 16 β•‘
154
+ β•‘ Effective batch: 32 β•‘
155
+ β•‘ Epochs : 1000
156
+
157
+ β•šβ•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•β•
158
+ """)
159
+
160
+ trainer.fit()
161
+ dist.destroy_process_group()
162
+
163
+
164
+ # ─────────────────────────────────────────
165
+ # ISHGA TUSHIRISH
166
+ # ─────────────────────────────────────────
167
+ if __name__ == "__main__":
168
+ world_size = torch.cuda.device_count()
169
+ print(f"πŸ–₯️ Topilgan GPU: {world_size} ta")
170
+
171
+ if world_size < 2:
172
+ print("⚠️ Faqat 1 GPU topildi! Kaggle Settings β†’ Accelerator β†’ GPU T4 x2 tanlang.")
173
+ # Baribir 1 GPU bilan ishlaydi
174
+ train(0, 1)
175
+ else:
176
+ # Ikkala GPU ni parallel ishga tushirish
177
+ mp.spawn(
178
+ train,
179
+ args=(world_size,),
180
+ nprocs=world_size,
181
+ join=True
182
+ )