nkululeko 0.86.3__py3-none-any.whl → 0.86.4__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- nkululeko/constants.py +1 -1
- nkululeko/demo.py +52 -2
- nkululeko/experiment.py +2 -1
- nkululeko/models/model_tuned.py +19 -13
- nkululeko/reporting/reporter.py +1 -1
- nkululeko/utils/util.py +15 -6
- {nkululeko-0.86.3.dist-info → nkululeko-0.86.4.dist-info}/METADATA +6 -1
- {nkululeko-0.86.3.dist-info → nkululeko-0.86.4.dist-info}/RECORD +11 -11
- {nkululeko-0.86.3.dist-info → nkululeko-0.86.4.dist-info}/LICENSE +0 -0
- {nkululeko-0.86.3.dist-info → nkululeko-0.86.4.dist-info}/WHEEL +0 -0
- {nkululeko-0.86.3.dist-info → nkululeko-0.86.4.dist-info}/top_level.txt +0 -0
nkululeko/constants.py
CHANGED
@@ -1,2 +1,2 @@
|
|
1
|
-
VERSION="0.86.
|
1
|
+
VERSION="0.86.4"
|
2
2
|
SAMPLING_RATE = 16000
|
nkululeko/demo.py
CHANGED
@@ -20,16 +20,20 @@ Options: \n
|
|
20
20
|
import argparse
|
21
21
|
import configparser
|
22
22
|
import os
|
23
|
+
import pandas as pd
|
23
24
|
|
24
25
|
from nkululeko.constants import VERSION
|
25
26
|
from nkululeko.experiment import Experiment
|
26
27
|
import nkululeko.glob_conf as glob_conf
|
27
28
|
from nkululeko.utils.util import Util
|
29
|
+
from transformers import pipeline
|
28
30
|
|
29
31
|
|
30
32
|
def main(src_dir):
|
31
|
-
parser = argparse.ArgumentParser(
|
32
|
-
|
33
|
+
parser = argparse.ArgumentParser(
|
34
|
+
description="Call the nkululeko DEMO framework.")
|
35
|
+
parser.add_argument("--config", default="exp.ini",
|
36
|
+
help="The base configuration")
|
33
37
|
parser.add_argument(
|
34
38
|
"--file", help="A file that should be processed (16kHz mono wav)"
|
35
39
|
)
|
@@ -79,6 +83,52 @@ def main(src_dir):
|
|
79
83
|
f" {VERSION}"
|
80
84
|
)
|
81
85
|
|
86
|
+
def print_pipe(files, outfile):
|
87
|
+
"""
|
88
|
+
Prints the pipeline output for a list of files, and optionally writes the results to an output file.
|
89
|
+
|
90
|
+
Args:
|
91
|
+
files (list): A list of file paths to process through the pipeline.
|
92
|
+
outfile (str, optional): The path to an output file to write the pipeline results to.
|
93
|
+
|
94
|
+
Returns:
|
95
|
+
None
|
96
|
+
"""
|
97
|
+
results = []
|
98
|
+
for file in files:
|
99
|
+
result = pipe(file, top_k=1)
|
100
|
+
if result[0]["score"] != result[0]["score"]: # Check for NaN
|
101
|
+
print(f"ERROR: NaN value in pipeline output for file: {file}")
|
102
|
+
else:
|
103
|
+
results.append(f"{file}, {result[0]['label']}")
|
104
|
+
print("\n".join(results))
|
105
|
+
|
106
|
+
if outfile is not None:
|
107
|
+
with open(outfile, "w") as f:
|
108
|
+
f.write("\n".join(results))
|
109
|
+
|
110
|
+
if util.get_model_type() == "finetune":
|
111
|
+
model_path = os.path.join(
|
112
|
+
util.get_exp_dir(), "models", "run_0", "torch")
|
113
|
+
pipe = pipeline("audio-classification", model=model_path)
|
114
|
+
if args.file is not None:
|
115
|
+
print_pipe([args.file], args.outfile)
|
116
|
+
elif args.list is not None:
|
117
|
+
# read audio files from list
|
118
|
+
print(f"Reading files from {args.list}")
|
119
|
+
list_file = pd.read_csv(args.list, header="infer")
|
120
|
+
files = list_file.iloc[:, 0].tolist()
|
121
|
+
print_pipe(files, args.outfile)
|
122
|
+
elif args.folder is not None:
|
123
|
+
# read audio files from folder
|
124
|
+
from nkululeko.utils.files import find_files
|
125
|
+
|
126
|
+
files = find_files(args.folder, relative=True, ext=["wav", "mp3"])
|
127
|
+
print_pipe(files, args.outfile)
|
128
|
+
else:
|
129
|
+
print("ERROR: input mic currently is not supported for finetuning")
|
130
|
+
return
|
131
|
+
|
82
132
|
# load the experiment
|
83
133
|
expr.load(f"{util.get_save_name()}")
|
84
134
|
if args.folder is not None:
|
nkululeko/experiment.py
CHANGED
@@ -115,7 +115,8 @@ class Experiment:
|
|
115
115
|
self.util.debug(f"Target labels (from config): {labels}")
|
116
116
|
else:
|
117
117
|
self.labels = auto_labels
|
118
|
-
|
118
|
+
# print autolabel no matter it is specified or not
|
119
|
+
self.util.debug(f"Target labels (from database): {auto_labels}")
|
119
120
|
glob_conf.set_labels(self.labels)
|
120
121
|
self.util.debug(f"loaded databases {dbs}")
|
121
122
|
|
nkululeko/models/model_tuned.py
CHANGED
@@ -54,9 +54,11 @@ class TunedModel(BaseModel):
|
|
54
54
|
self.learning_rate = float(
|
55
55
|
self.util.config_val("MODEL", "learning_rate", "0.0001")
|
56
56
|
)
|
57
|
-
self.max_duration = float(
|
57
|
+
self.max_duration = float(
|
58
|
+
self.util.config_val("MODEL", "max_duration", "8.0"))
|
58
59
|
self.df_train, self.df_test = df_train, df_test
|
59
60
|
self.epoch_num = int(self.util.config_val("EXP", "epochs", 1))
|
61
|
+
self.util.debug(f"num of epochs: {self.epoch_num}")
|
60
62
|
drop = self.util.config_val("MODEL", "drop", False)
|
61
63
|
self.drop = 0.1
|
62
64
|
if drop:
|
@@ -137,7 +139,6 @@ class TunedModel(BaseModel):
|
|
137
139
|
if self.push:
|
138
140
|
tokenizer.push_to_hub(self.util.get_name())
|
139
141
|
|
140
|
-
|
141
142
|
feature_extractor = transformers.Wav2Vec2FeatureExtractor(
|
142
143
|
feature_size=1,
|
143
144
|
sampling_rate=16000,
|
@@ -267,7 +268,8 @@ class TunedModel(BaseModel):
|
|
267
268
|
else:
|
268
269
|
criterion = torch.nn.CrossEntropyLoss()
|
269
270
|
else:
|
270
|
-
self.util.error(
|
271
|
+
self.util.error(
|
272
|
+
f"criterion {criterion} not supported for classifier")
|
271
273
|
else:
|
272
274
|
self.criterion = self.util.config_val("MODEL", "loss", "ccc")
|
273
275
|
if criterion == "1-ccc":
|
@@ -277,7 +279,8 @@ class TunedModel(BaseModel):
|
|
277
279
|
elif criterion == "mae":
|
278
280
|
criterion = torch.nn.L1Loss()
|
279
281
|
else:
|
280
|
-
self.util.error(
|
282
|
+
self.util.error(
|
283
|
+
f"criterion {criterion} not supported for regressor")
|
281
284
|
|
282
285
|
# set push_to_hub value, default false
|
283
286
|
# push = eval(self.util.config_val("MODEL", "push_to_hub", "False"))
|
@@ -316,17 +319,19 @@ class TunedModel(BaseModel):
|
|
316
319
|
elif metrics_for_best_model == "MAE":
|
317
320
|
greater_is_better = False
|
318
321
|
else:
|
319
|
-
self.util.error(
|
322
|
+
self.util.error(
|
323
|
+
f"unknown metric/measure: {metrics_for_best_model}")
|
320
324
|
|
321
325
|
training_args = transformers.TrainingArguments(
|
322
|
-
output_dir=
|
326
|
+
output_dir=model_root,
|
323
327
|
logging_dir=self.log_root,
|
324
328
|
per_device_train_batch_size=self.batch_size,
|
325
329
|
per_device_eval_batch_size=self.batch_size,
|
326
330
|
gradient_accumulation_steps=self.accumulation_steps,
|
327
331
|
evaluation_strategy="steps",
|
328
332
|
num_train_epochs=self.epoch_num,
|
329
|
-
fp16=self.device
|
333
|
+
fp16=self.device != "cpu",
|
334
|
+
use_cpu=self.device == "cpu",
|
330
335
|
save_steps=num_steps,
|
331
336
|
eval_steps=num_steps,
|
332
337
|
logging_steps=num_steps,
|
@@ -340,6 +345,7 @@ class TunedModel(BaseModel):
|
|
340
345
|
report_to="none",
|
341
346
|
push_to_hub=self.push,
|
342
347
|
hub_model_id=f"{self.util.get_name()}",
|
348
|
+
overwrite_output_dir=True,
|
343
349
|
)
|
344
350
|
|
345
351
|
trainer = Trainer(
|
@@ -354,7 +360,7 @@ class TunedModel(BaseModel):
|
|
354
360
|
)
|
355
361
|
|
356
362
|
trainer.train()
|
357
|
-
|
363
|
+
trainer.save_model(self.torch_root)
|
358
364
|
log_file = os.path.join(
|
359
365
|
self.log_root,
|
360
366
|
"log.txt",
|
@@ -447,7 +453,7 @@ class TunedModel(BaseModel):
|
|
447
453
|
self.clf = pickle.load(handle)
|
448
454
|
|
449
455
|
|
450
|
-
@dataclasses.dataclass
|
456
|
+
@ dataclasses.dataclass
|
451
457
|
class ModelOutput(transformers.file_utils.ModelOutput):
|
452
458
|
|
453
459
|
logits: torch.FloatTensor = None
|
@@ -455,7 +461,7 @@ class ModelOutput(transformers.file_utils.ModelOutput):
|
|
455
461
|
cnn_features: torch.FloatTensor = None
|
456
462
|
|
457
463
|
|
458
|
-
@dataclasses.dataclass
|
464
|
+
@ dataclasses.dataclass
|
459
465
|
class ModelOutputReg(transformers.file_utils.ModelOutput):
|
460
466
|
|
461
467
|
logits: torch.FloatTensor
|
@@ -524,9 +530,9 @@ class Model(Wav2Vec2PreTrainedModel):
|
|
524
530
|
)
|
525
531
|
outputs = torch.sum(hidden_states, dim=1)
|
526
532
|
attention_sum = torch.sum(attention_mask, dim=1)
|
527
|
-
|
528
|
-
epsilon = 1e-6
|
529
|
-
outputs = outputs / (torch.reshape(attention_sum, (-1, 1)) +
|
533
|
+
|
534
|
+
epsilon = 1e-6 # to avoid division by zero and numerical instability
|
535
|
+
outputs = outputs / (torch.reshape(attention_sum, (-1, 1)) +
|
530
536
|
epsilon)
|
531
537
|
|
532
538
|
return outputs
|
nkululeko/reporting/reporter.py
CHANGED
@@ -315,7 +315,7 @@ class Reporter:
|
|
315
315
|
plt.savefig(plot_path)
|
316
316
|
self.util.debug(f"plotted epoch progression to {plot_path}")
|
317
317
|
plt.close(fig)
|
318
|
-
fig.clear()
|
318
|
+
# fig.clear()
|
319
319
|
|
320
320
|
def plot_epoch_progression(self, reports, out_name):
|
321
321
|
fig_dir = self.util.get_path("fig_dir")
|
nkululeko/utils/util.py
CHANGED
@@ -37,7 +37,8 @@ class Util:
|
|
37
37
|
import nkululeko.glob_conf as glob_conf
|
38
38
|
|
39
39
|
self.config = glob_conf.config
|
40
|
-
self.got_data_roots = self.config_val(
|
40
|
+
self.got_data_roots = self.config_val(
|
41
|
+
"DATA", "root_folders", False)
|
41
42
|
if self.got_data_roots:
|
42
43
|
# if there is a global data rootfolder file, read from there
|
43
44
|
if not os.path.isfile(self.got_data_roots):
|
@@ -116,7 +117,8 @@ class Util:
|
|
116
117
|
)
|
117
118
|
return default
|
118
119
|
if not default in self.stopvals:
|
119
|
-
self.debug(
|
120
|
+
self.debug(
|
121
|
+
f"value for {key} not found, using default: {default}")
|
120
122
|
return default
|
121
123
|
|
122
124
|
def set_config(self, config):
|
@@ -159,8 +161,10 @@ class Util:
|
|
159
161
|
if len(df) == 0:
|
160
162
|
return df
|
161
163
|
if not isinstance(df.index, pd.MultiIndex):
|
162
|
-
self.debug(
|
163
|
-
|
164
|
+
self.debug(
|
165
|
+
"converting to segmented index, this might take a while...")
|
166
|
+
df.index = audformat.utils.to_segmented_index(
|
167
|
+
df.index, allow_nat=False)
|
164
168
|
return df
|
165
169
|
|
166
170
|
def _get_value_descript(self, section, name):
|
@@ -195,6 +199,9 @@ class Util:
|
|
195
199
|
return_string = return_string + "_" + mt
|
196
200
|
return return_string.replace("__", "_")
|
197
201
|
|
202
|
+
def get_model_type(self):
|
203
|
+
return self.config["MODEL"]["type"]
|
204
|
+
|
198
205
|
def get_model_description(self):
|
199
206
|
mt = ""
|
200
207
|
mt = f'{self.config["MODEL"]["type"]}'
|
@@ -271,7 +278,8 @@ class Util:
|
|
271
278
|
return self.config[section][key]
|
272
279
|
except KeyError:
|
273
280
|
if default not in self.stopvals:
|
274
|
-
self.debug(
|
281
|
+
self.debug(
|
282
|
+
f"value for {key} not found, using default: {default}")
|
275
283
|
return default
|
276
284
|
|
277
285
|
def config_val_list(self, section, key, default):
|
@@ -279,7 +287,8 @@ class Util:
|
|
279
287
|
return ast.literal_eval(self.config[section][key])
|
280
288
|
except KeyError:
|
281
289
|
if not default in self.stopvals:
|
282
|
-
self.debug(
|
290
|
+
self.debug(
|
291
|
+
f"value for {key} not found, using default: {default}")
|
283
292
|
return default
|
284
293
|
|
285
294
|
def continuous_to_categorical(self, series):
|
@@ -1,6 +1,6 @@
|
|
1
1
|
Metadata-Version: 2.1
|
2
2
|
Name: nkululeko
|
3
|
-
Version: 0.86.
|
3
|
+
Version: 0.86.4
|
4
4
|
Summary: Machine learning audio prediction experiments based on templates
|
5
5
|
Home-page: https://github.com/felixbur/nkululeko
|
6
6
|
Author: Felix Burkhardt
|
@@ -237,6 +237,7 @@ There's my [blog](http://blog.syntheticspeech.de/?s=nkululeko) with tutorials:
|
|
237
237
|
* [Run multiple experiments in one go](http://blog.syntheticspeech.de/2022/03/28/how-to-run-multiple-experiments-in-one-go-with-nkululeko/)
|
238
238
|
* [Compare several MLP layer layouts with each other](http://blog.syntheticspeech.de/2022/04/11/how-to-compare-several-mlp-layer-layouts-with-each-other/)
|
239
239
|
* [Import features from outside the software](http://blog.syntheticspeech.de/2022/10/18/how-to-import-features-from-outside-the-nkululeko-software/)
|
240
|
+
* [Export acoustic features](http://blog.syntheticspeech.de/2024/05/30/nkululeko-export-acoustic-features/)
|
240
241
|
* [Explore feature importance](http://blog.syntheticspeech.de/2023/02/20/nkululeko-show-feature-importance/)
|
241
242
|
* [Plot distributions for feature values](http://blog.syntheticspeech.de/2023/02/16/nkululeko-how-to-plot-distributions-of-feature-values/)
|
242
243
|
* [Show feature importance](http://blog.syntheticspeech.de/2023/02/20/nkululeko-show-feature-importance/)
|
@@ -334,6 +335,10 @@ F. Burkhardt, Johannes Wagner, Hagen Wierstorf, Florian Eyben and Björn Schulle
|
|
334
335
|
Changelog
|
335
336
|
=========
|
336
337
|
|
338
|
+
Version 0.86.4
|
339
|
+
--------------
|
340
|
+
* add finetuning to the demo module
|
341
|
+
|
337
342
|
Version 0.86.3
|
338
343
|
--------------
|
339
344
|
* bugfixed: nan in finetuned model and double saving
|
@@ -2,11 +2,11 @@ nkululeko/__init__.py,sha256=62f8HiEzJ8rG2QlTFJXUCMpvuH3fKI33DoJSj33mscc,63
|
|
2
2
|
nkululeko/aug_train.py,sha256=YhuZnS_WVWnun9G-M6g5n6rbRxoVREz6Zh7k6qprFNQ,3194
|
3
3
|
nkululeko/augment.py,sha256=4MG0apTAG5RgkuJrYEjGgDdbodZWi_HweSPNI1JJ5QA,3051
|
4
4
|
nkululeko/cacheddataset.py,sha256=lIJ6hUo5LoxSrzXtWV8mzwO7wRtUETWnOQ4ws2XfL1E,969
|
5
|
-
nkululeko/constants.py,sha256=
|
6
|
-
nkululeko/demo.py,sha256=
|
5
|
+
nkululeko/constants.py,sha256=QtEoU6iCjnUpcJT-FOh4bU4miJ_D0z26OpSub4oEY1c,39
|
6
|
+
nkululeko/demo.py,sha256=WSKr-W5uJ9DQfemK923g7Hd5V3kgAn03Er0JX1Pa45I,5142
|
7
7
|
nkululeko/demo_feats.py,sha256=sAeGFojhEj9WEDFtG3SzPBmyYJWLF2rkbpp65m8Ujo4,2025
|
8
8
|
nkululeko/demo_predictor.py,sha256=es56xbT8ifkS_vnrlb5NTZT54gNmeUtNlA4zVA_gnN8,4757
|
9
|
-
nkululeko/experiment.py,sha256=
|
9
|
+
nkululeko/experiment.py,sha256=huhHLQfnzxRJlQi2SY61XMWbC8xEWpe31yq9spBUk-4,31041
|
10
10
|
nkululeko/explore.py,sha256=lDzRoW_Taa5u4BBABZLD89BcQWnYlrftJR4jgt1yyj0,2609
|
11
11
|
nkululeko/export.py,sha256=mHeEAAmtZuxdyebLlbSzPrHSi9OMgJHbk35d3DTxRBc,4632
|
12
12
|
nkululeko/feature_extractor.py,sha256=8mssYKmo4LclVI-hiLmJEDZ0ZPyDavFG2YwtXcrGzwM,3976
|
@@ -88,7 +88,7 @@ nkululeko/models/model_svm.py,sha256=rsME3KvKvNG7bdE5lbvYUu85WZhaASZxxmdNDIVJRZ4
|
|
88
88
|
nkululeko/models/model_svr.py,sha256=_YZeksqB3eBENGlg3g9RwYFlk9rQQ-XCeNBKLlGGVoE,725
|
89
89
|
nkululeko/models/model_tree.py,sha256=rf16faUm4o2LJgkoYpeY998b8DQIvXZ73_m1IS3TnnE,417
|
90
90
|
nkululeko/models/model_tree_reg.py,sha256=IgQcPTE-304HQLYSKPF8Z4ot_Ur9dH01fZjS0nXke_M,428
|
91
|
-
nkululeko/models/model_tuned.py,sha256=
|
91
|
+
nkululeko/models/model_tuned.py,sha256=vmNBkqvEH-4nnhY1REXDA9kA4vpZJzeRmGJFq7E3bLM,21340
|
92
92
|
nkululeko/models/model_xgb.py,sha256=Thgx5ESdIok4v72mKh4plxpo4smGcKALWNCJTDScY0M,447
|
93
93
|
nkululeko/models/model_xgr.py,sha256=aGBtNGLWjOE_2rICGYGFxmT8DtnHYsIl1lIpMtghHsY,418
|
94
94
|
nkululeko/reporting/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
@@ -96,7 +96,7 @@ nkululeko/reporting/defines.py,sha256=IsY1YgKRMaABpylVKjBJgJ5bNCEbGCVA_E6pivraqS
|
|
96
96
|
nkululeko/reporting/latex_writer.py,sha256=qiCRSmB4KOD_za4oHu5x-PhwjZohzfo8wecMOwlXZwc,1886
|
97
97
|
nkululeko/reporting/report.py,sha256=W0rcigDdjBvxZQ3pZja_gvToILYvaZ1BFtnN2qFRfYI,1060
|
98
98
|
nkululeko/reporting/report_item.py,sha256=siWeGNgo4bAE46YBMNcsdf3jTMTy76BO9Fi6DTvDig4,533
|
99
|
-
nkululeko/reporting/reporter.py,sha256=
|
99
|
+
nkululeko/reporting/reporter.py,sha256=4dXRwJ-CZ49NlF_kv9hfDjZT3bbWNNMyNpKEBLKs3Ew,13447
|
100
100
|
nkululeko/reporting/result.py,sha256=nSN5or-Py2GPRWHkWpGRh7UCi1W0er7WLEHz8fYLk-A,742
|
101
101
|
nkululeko/segmenting/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
102
102
|
nkululeko/segmenting/seg_inaspeechsegmenter.py,sha256=pmLHuXsaqvcdYxB4PSW9l1mbQWZZBJFhi_CGabqydas,1947
|
@@ -104,9 +104,9 @@ nkululeko/segmenting/seg_silero.py,sha256=lLytS38KzARS17omwv8VBw-zz60RVSXGSvZ5Ev
|
|
104
104
|
nkululeko/utils/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
105
105
|
nkululeko/utils/files.py,sha256=UiGAtZRWYjHSvlmPaTMtzyNNGE6qaLaxQkybctS7iRM,4021
|
106
106
|
nkululeko/utils/stats.py,sha256=1yUq0FTOyqkU8TwUocJRYdJaqMU5SlOBBRUun9STo2M,2829
|
107
|
-
nkululeko/utils/util.py,sha256=
|
108
|
-
nkululeko-0.86.
|
109
|
-
nkululeko-0.86.
|
110
|
-
nkululeko-0.86.
|
111
|
-
nkululeko-0.86.
|
112
|
-
nkululeko-0.86.
|
107
|
+
nkululeko/utils/util.py,sha256=ILpfNuaeq-hy1bUkRhVrzO2wG9z9Upaozs9EBoIaMG0,14123
|
108
|
+
nkululeko-0.86.4.dist-info/LICENSE,sha256=0zGP5B_W35yAcGfHPS18Q2B8UhvLRY3dQq1MhpsJU_U,1076
|
109
|
+
nkululeko-0.86.4.dist-info/METADATA,sha256=D1y8wrwDr0gLVdafV4E_GcER5yrt3IaKUdqJ8huMCwA,37480
|
110
|
+
nkululeko-0.86.4.dist-info/WHEEL,sha256=GJ7t_kWBFywbagK5eo9IoUwLW6oyOeTKmQ-9iHFVNxQ,92
|
111
|
+
nkululeko-0.86.4.dist-info/top_level.txt,sha256=DPFNNSHPjUeVKj44dVANAjuVGRCC3MusJ08lc2a8xFA,10
|
112
|
+
nkululeko-0.86.4.dist-info/RECORD,,
|
File without changes
|
File without changes
|
File without changes
|