nkululeko 0.94.1__py3-none-any.whl → 0.94.3__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.
Files changed (40) hide show
  1. examples/__init__.py +0 -0
  2. nkululeko/augmenting/randomsplicer.py +1 -1
  3. nkululeko/augmenting/randomsplicing.py +1 -1
  4. nkululeko/augmenting/resampler.py +22 -14
  5. nkululeko/autopredict/ap_age.py +1 -1
  6. nkululeko/autopredict/ap_arousal.py +1 -1
  7. nkululeko/autopredict/ap_gender.py +1 -1
  8. nkululeko/autopredict/ap_mos.py +1 -1
  9. nkululeko/autopredict/ap_pesq.py +1 -1
  10. nkululeko/autopredict/ap_sdr.py +2 -2
  11. nkululeko/autopredict/ap_sid.py +1 -1
  12. nkululeko/autopredict/ap_snr.py +1 -1
  13. nkululeko/autopredict/ap_stoi.py +1 -1
  14. nkululeko/autopredict/ap_valence.py +1 -1
  15. nkululeko/constants.py +1 -1
  16. nkululeko/demo.py +7 -7
  17. nkululeko/experiment.py +2 -1
  18. nkululeko/feat_extract/feats_emotion2vec.py +218 -0
  19. nkululeko/feat_extract/feats_mos.py +2 -2
  20. nkululeko/feat_extract/feats_snr.py +1 -1
  21. nkululeko/feature_extractor.py +2 -2
  22. nkululeko/models/model.py +42 -4
  23. nkululeko/models/model_cnn.py +1 -1
  24. nkululeko/models/model_xgb.py +1 -1
  25. nkululeko/models/tests/__init__.py +0 -0
  26. nkululeko/models/tests/test_model_svm.py +56 -0
  27. nkululeko/nkululeko.py +13 -2
  28. nkululeko/reporting/report_item.py +1 -1
  29. nkululeko/runmanager.py +19 -9
  30. nkululeko/scaler.py +22 -14
  31. nkululeko/test_predictor.py +1 -1
  32. nkululeko/utils/unzip.py +38 -0
  33. nkululeko/utils/util.py +19 -5
  34. nkululeko-0.94.3.dist-info/METADATA +76 -0
  35. {nkululeko-0.94.1.dist-info → nkululeko-0.94.3.dist-info}/RECORD +39 -34
  36. {nkululeko-0.94.1.dist-info → nkululeko-0.94.3.dist-info}/WHEEL +1 -1
  37. {nkululeko-0.94.1.dist-info → nkululeko-0.94.3.dist-info}/top_level.txt +1 -0
  38. nkululeko-0.94.1.dist-info/METADATA +0 -40
  39. {nkululeko-0.94.1.dist-info → nkululeko-0.94.3.dist-info}/entry_points.txt +0 -0
  40. {nkululeko-0.94.1.dist-info → nkululeko-0.94.3.dist-info}/licenses/LICENSE +0 -0
examples/__init__.py ADDED
File without changes
@@ -5,7 +5,7 @@ Code originally by Oliver Pauly
5
5
 
6
6
  Based on an idea by Klaus Scherer
7
7
 
8
- K. R. Scherer, “Randomized splicing: A note on a simple technique for masking speech content”
8
+ K. R. Scherer, “Randomized splicing: A note on a simple technique for masking speech content”
9
9
  Journal of Experimental Research in Personality, vol. 5, pp. 155–159, 1971.
10
10
 
11
11
  Evaluated in:
@@ -3,7 +3,7 @@ Code originally by Oliver Pauly
3
3
 
4
4
  Based on an idea by Klaus Scherer
5
5
 
6
- K. R. Scherer, “Randomized splicing: A note on a simple technique for masking speech content”
6
+ K. R. Scherer, “Randomized splicing: A note on a simple technique for masking speech content”
7
7
  Journal of Experimental Research in Personality, vol. 5, pp. 155–159, 1971.
8
8
 
9
9
  Evaluated in:
@@ -17,7 +17,7 @@ class Resampler:
17
17
  def __init__(self, df, replace, not_testing=True):
18
18
  self.SAMPLING_RATE = 16000
19
19
  self.df = df
20
- self.util = Util("resampler", has_config=not_testing)
20
+ self.util = Util("resampler", has_config=not not_testing)
21
21
  self.util.warn(f"all files might be resampled to {self.SAMPLING_RATE}")
22
22
  self.not_testing = not_testing
23
23
  self.replace = (
@@ -30,7 +30,7 @@ class Resampler:
30
30
  files = self.df.index.get_level_values(0).values
31
31
  # replace = eval(self.util.config_val("RESAMPLE", "replace", "False"))
32
32
  replace = self.replace
33
- if self.not_testing:
33
+ if not self.not_testing:
34
34
  store = self.util.get_path("store")
35
35
  else:
36
36
  store = "./"
@@ -67,17 +67,25 @@ class Resampler:
67
67
  self.df = self.df.set_index(
68
68
  self.df.index.set_levels(new_files, level="file")
69
69
  )
70
- target_file = self.util.config_val("RESAMPLE", "target", "resampled.csv")
71
- # remove encoded labels
72
- target = self.util.config_val("DATA", "target", "emotion")
73
- if "class_label" in self.df.columns:
74
- self.df = self.df.drop(columns=[target])
75
- self.df = self.df.rename(columns={"class_label": target})
76
- # save file
77
- self.df.to_csv(target_file)
78
- self.util.debug(
79
- "saved resampled list of files to" f" {os.path.abspath(target_file)}"
80
- )
70
+ if not self.not_testing:
71
+ target_file = self.util.config_val("RESAMPLE", "target", "resampled.csv")
72
+ # remove encoded labels
73
+ target = self.util.config_val("DATA", "target", "emotion")
74
+ if "class_label" in self.df.columns:
75
+ self.df = self.df.drop(columns=[target])
76
+ self.df = self.df.rename(columns={"class_label": target})
77
+ # save file
78
+ self.df.to_csv(target_file)
79
+ self.util.debug(
80
+ "saved resampled list of files to" f" {os.path.abspath(target_file)}"
81
+ )
82
+ else:
83
+ # When running from command line, save to simple resampled.csv
84
+ target_file = "resampled.csv"
85
+ self.df.to_csv(target_file)
86
+ self.util.debug(
87
+ f"saved resampled list of files to {os.path.abspath(target_file)}"
88
+ )
81
89
  self.util.debug(f"resampled {succes} files, {error} errors")
82
90
 
83
91
 
@@ -91,7 +99,7 @@ def main():
91
99
  df_sample.index, allow_nat=False
92
100
  )
93
101
  df_sample.head(10)
94
- resampler = Resampler(df_sample, not_testing=False)
102
+ resampler = Resampler(df_sample, False, not_testing=False)
95
103
  resampler.resample()
96
104
  shutil.copyfile(testfile, "tmp.resample_result.wav")
97
105
  shutil.copyfile("tmp.wav", testfile)
@@ -1,4 +1,4 @@
1
- """"
1
+ """ "
2
2
  A predictor for age.
3
3
  Currently based on audEERING's agender model.
4
4
  """
@@ -1,4 +1,4 @@
1
- """"
1
+ """ "
2
2
  A predictor for emotional arousal.
3
3
  Currently based on audEERING's emotional dimension model.
4
4
  """
@@ -1,4 +1,4 @@
1
- """"
1
+ """ "
2
2
  A predictor for biological sex.
3
3
  Currently based on audEERING's agender model.
4
4
  """
@@ -1,4 +1,4 @@
1
- """"
1
+ """ "
2
2
  A predictor for MOS - mean opinion score.
3
3
  """
4
4
 
@@ -1,4 +1,4 @@
1
- """"
1
+ """ "
2
2
  A predictor for PESQ - Perceptual Evaluation of Speech Quality.
3
3
  """
4
4
 
@@ -1,6 +1,6 @@
1
- """"
1
+ """ "
2
2
  A predictor for SDR - Signal to Distortion Ratio.
3
- as estimated by Scale-Invariant Signal-to-Distortion Ratio (SI-SDR)
3
+ as estimated by Scale-Invariant Signal-to-Distortion Ratio (SI-SDR)
4
4
  """
5
5
 
6
6
  import ast
@@ -1,4 +1,4 @@
1
- """"
1
+ """ "
2
2
  A predictor for sid - Speaker ID.
3
3
  """
4
4
 
@@ -1,4 +1,4 @@
1
- """"
1
+ """ "
2
2
  A predictor for SNR - signal-to-noise ratio.
3
3
  """
4
4
 
@@ -1,4 +1,4 @@
1
- """"
1
+ """ "
2
2
  A predictor for STOI - Short-Time Objective Intelligibility (STOI)
3
3
  """
4
4
 
@@ -1,4 +1,4 @@
1
- """"
1
+ """ "
2
2
  A predictor for emotional valence.
3
3
  Currently based on audEERING's emotional dimension model.
4
4
  """
nkululeko/constants.py CHANGED
@@ -1,2 +1,2 @@
1
- VERSION="0.94.1"
1
+ VERSION="0.94.3"
2
2
  SAMPLING_RATE = 16000
nkululeko/demo.py CHANGED
@@ -7,15 +7,15 @@
7
7
  And run it in demo mode.
8
8
  It requires the project config file to be run before.
9
9
 
10
- Usage:
11
- python -m nkululeko.demo [--config CONFIG] [--file FILE] [--list LIST] [--folder FOLDER] [--outfile OUTFILE]
10
+ Usage:
11
+ python -m nkululeko.demo [--config CONFIG] [--file FILE] [--list LIST] [--folder FOLDER] [--outfile OUTFILE]
12
12
 
13
13
  Options: \n
14
- --config CONFIG The base configuration file (default: exp.ini) \n
15
- --file FILE A file that should be processed (16kHz mono wav) \n
16
- --list LIST A file with a list of files, one per line, that should be processed (16kHz mono wav) \n
17
- --folder FOLDER A name of a folder where the files within the list are in (default: ./) \n
18
- --outfile OUTFILE A filename to store the results in CSV (default: None)
14
+ --config CONFIG The base configuration file (default: exp.ini) \n
15
+ --file FILE A file that should be processed (16kHz mono wav) \n
16
+ --list LIST A file with a list of files, one per line, that should be processed (16kHz mono wav) \n
17
+ --folder FOLDER A name of a folder where the files within the list are in (default: ./) \n
18
+ --outfile OUTFILE A filename to store the results in CSV (default: None)
19
19
  """
20
20
  import argparse
21
21
  import configparser
nkululeko/experiment.py CHANGED
@@ -1,4 +1,4 @@
1
- # experiment.py: Main class for an experiment (nkululeko.nkululeko)
1
+ # nkululeko/experiment.py: Main class for an experiment (nkululeko.nkululeko)
2
2
  import ast
3
3
  import os
4
4
  import pickle
@@ -380,6 +380,7 @@ class Experiment:
380
380
  self.util.debug(
381
381
  f"train/test shape: {self.df_train.shape}/{self.df_test.shape}"
382
382
  )
383
+
383
384
  def _add_random_target(self, df):
384
385
  labels = glob_conf.labels
385
386
  a = [None] * len(df)
@@ -0,0 +1,218 @@
1
+ # feats_emotion2vec.py
2
+ # emotion2vec feature extractor for Nkululeko
3
+ # choices for feat_type = "emotion2vec", "emotion2vec-large", "emotion2vec-base", "emotion2vec-seed"
4
+
5
+ # requirements:
6
+ # pip install "modelscope>=1.9.5,<2.0.0"
7
+ # pip install funasr
8
+
9
+ import os
10
+
11
+ import numpy as np
12
+ import pandas as pd
13
+ import torch
14
+ import torchaudio
15
+ from tqdm import tqdm
16
+
17
+ import nkululeko.glob_conf as glob_conf
18
+ from nkululeko.feat_extract.featureset import Featureset
19
+
20
+
21
+ class Emotion2vec(Featureset):
22
+ """Class to extract emotion2vec embeddings."""
23
+
24
+ def __init__(self, name, data_df, feat_type):
25
+ """Constructor.
26
+
27
+ Is_train is needed to distinguish from test/dev sets,
28
+ because they use the codebook from the training.
29
+ """
30
+ super().__init__(name, data_df, feat_type)
31
+ # check if device is not set, use cuda if available
32
+ cuda = "cuda" if torch.cuda.is_available() else "cpu"
33
+ self.device = self.util.config_val("MODEL", "device", cuda)
34
+ self.model_initialized = False
35
+ self.feat_type = feat_type
36
+
37
+ def init_model(self):
38
+ # load model
39
+ self.util.debug("loading emotion2vec model...")
40
+
41
+ try:
42
+ from funasr import AutoModel
43
+ except ImportError:
44
+ self.util.error(
45
+ "FunASR is required for emotion2vec features. "
46
+ "Please install with: pip install funasr modelscope"
47
+ )
48
+
49
+ # Map feat_type to model names
50
+ model_mapping = {
51
+ "emotion2vec": "iic/emotion2vec_base",
52
+ "emotion2vec-base": "iic/emotion2vec_base_finetuned",
53
+ "emotion2vec-seed": "iic/emotion2vec_plus_seed",
54
+ "emotion2vec-large": "iic/emotion2vec_plus_large",
55
+ }
56
+
57
+ # Get model path from config or use default mapping
58
+ model_path = self.util.config_val(
59
+ "FEATS",
60
+ "emotion2vec.model",
61
+ model_mapping.get(self.feat_type, "iic/emotion2vec_base"),
62
+ )
63
+
64
+ try:
65
+ # Initialize the FunASR model for emotion2vec
66
+ self.model = AutoModel(model=model_path)
67
+ self.util.debug(f"initialized emotion2vec model: {model_path}")
68
+ self.model_initialized = True
69
+ except Exception as e:
70
+ self.util.error(f"Failed to load emotion2vec model: {str(e)}")
71
+
72
+ def extract(self):
73
+ """Extract the features or load them from disk if present."""
74
+ store = self.util.get_path("store")
75
+ storage = f"{store}{self.name}.pkl"
76
+ extract = self.util.config_val("FEATS", "needs_feature_extraction", False)
77
+ no_reuse = self.util.config_val("FEATS", "no_reuse", "False") == "True"
78
+ if extract or no_reuse or not os.path.isfile(storage):
79
+ if not self.model_initialized:
80
+ self.init_model()
81
+ self.util.debug(
82
+ "extracting emotion2vec embeddings, this might take a while..."
83
+ )
84
+ emb_series = pd.Series(index=self.data_df.index, dtype=object)
85
+ length = len(self.data_df.index)
86
+ for idx, (file, start, end) in enumerate(
87
+ tqdm(self.data_df.index.to_list())
88
+ ):
89
+ emb = self.extract_embedding(file, start, end)
90
+ emb_series.iloc[idx] = emb
91
+ self.df = pd.DataFrame(emb_series.values.tolist(), index=self.data_df.index)
92
+ self.df.to_pickle(storage)
93
+ try:
94
+ glob_conf.config["DATA"]["needs_feature_extraction"] = "false"
95
+ except KeyError:
96
+ pass
97
+ else:
98
+ self.util.debug(f"reusing extracted {self.feat_type} embeddings")
99
+ self.df = pd.read_pickle(storage)
100
+ if self.df.isnull().values.any():
101
+ nanrows = self.df.columns[self.df.isna().any()].tolist()
102
+ print(nanrows)
103
+ self.util.error(
104
+ f"got nan: {self.df.shape} {self.df.isnull().sum().sum()}"
105
+ )
106
+
107
+ def extract_embedding(self, file, start, end):
108
+ """Extract embeddings directly from audio file."""
109
+ try:
110
+ # Handle segment extraction if needed
111
+ if hasattr(start, "total_seconds") and hasattr(end, "total_seconds"):
112
+ # Load audio segment
113
+ _, sampling_rate = torchaudio.load(file, frame_offset=0, num_frames=-1)
114
+ start_sample = int(start.total_seconds() * sampling_rate)
115
+ num_samples = int((end - start).total_seconds() * sampling_rate)
116
+ signal, sampling_rate = torchaudio.load(
117
+ file, frame_offset=start_sample, num_frames=num_samples
118
+ )
119
+
120
+ # Resample to 16kHz if needed
121
+ if sampling_rate != 16000:
122
+ resampler = torchaudio.transforms.Resample(sampling_rate, 16000)
123
+ signal = resampler(signal)
124
+ sampling_rate = 16000
125
+
126
+ # Convert to numpy and save as temporary file
127
+ signal_np = signal.squeeze().numpy()
128
+ if signal_np.ndim > 1:
129
+ signal_np = signal_np[0] # Take first channel if stereo
130
+
131
+ import tempfile
132
+ import soundfile as sf
133
+
134
+ with tempfile.NamedTemporaryFile(suffix=".wav", delete=False) as tmp_file:
135
+ sf.write(tmp_file.name, signal_np, sampling_rate)
136
+ audio_path = tmp_file.name
137
+ else:
138
+ # Use full file directly
139
+ audio_path = file
140
+
141
+ try:
142
+ # Extract features using FunASR emotion2vec model
143
+ res = self.model.generate(
144
+ audio_path, granularity="utterance", extract_embedding=True
145
+ )
146
+
147
+ # Get the embeddings from the result
148
+ if isinstance(res, list) and len(res) > 0:
149
+ embeddings = res[0].get("feats", None)
150
+ if embeddings is not None:
151
+ if isinstance(embeddings, list):
152
+ embeddings = np.array(embeddings)
153
+ return embeddings.flatten()
154
+ else:
155
+ # Fallback to create default embedding
156
+ return np.array([0.0] * 768)
157
+ else:
158
+ self.util.error(f"No result from emotion2vec model for file: {file}")
159
+ return np.array([0.0] * 768)
160
+
161
+ finally:
162
+ # Clean up temporary file if we created one
163
+ if hasattr(start, "total_seconds") and hasattr(end, "total_seconds"):
164
+ os.unlink(audio_path)
165
+
166
+ except Exception as e:
167
+ print(f"Error processing {file}: {str(e)}")
168
+ self.util.error(f"couldn't extract file: {file}, error: {str(e)}")
169
+ return np.array([0.0] * 768)
170
+
171
+ def extract_sample(self, signal, sr):
172
+ """Extract features from a single sample."""
173
+ if not self.model_initialized:
174
+ self.init_model()
175
+
176
+ # Save signal as temporary file for emotion2vec
177
+ import tempfile
178
+ import soundfile as sf
179
+
180
+ try:
181
+ # Convert tensor to numpy if needed
182
+ if torch.is_tensor(signal):
183
+ signal_np = signal.squeeze().numpy()
184
+ else:
185
+ signal_np = signal.squeeze()
186
+
187
+ # Handle multi-channel audio
188
+ if signal_np.ndim > 1:
189
+ signal_np = signal_np[0]
190
+
191
+ with tempfile.NamedTemporaryFile(suffix=".wav", delete=False) as tmp_file:
192
+ sf.write(tmp_file.name, signal_np, sr)
193
+
194
+ # Extract using the emotion2vec model
195
+ res = self.model.generate(
196
+ tmp_file.name, granularity="utterance", extract_embedding=True
197
+ )
198
+
199
+ # Get embeddings from result
200
+ if isinstance(res, list) and len(res) > 0:
201
+ embeddings = res[0].get("feats", None)
202
+ if embeddings is not None:
203
+ if isinstance(embeddings, list):
204
+ embeddings = np.array(embeddings)
205
+ return embeddings.flatten()
206
+
207
+ return np.array([0.0] * 768)
208
+
209
+ except Exception as e:
210
+ print(f"Error in extract_sample: {str(e)}")
211
+ return np.array([0.0] * 768)
212
+ finally:
213
+ # Clean up temporary file
214
+ if tmp_file is not None: # Check if tmp_file was created
215
+ try:
216
+ os.unlink(tmp_file.name)
217
+ except:
218
+ pass
@@ -1,11 +1,11 @@
1
- """ feats_mos.py
1
+ """feats_mos.py
2
2
  predict MOS (mean opinion score)
3
3
 
4
4
  adapted from
5
5
  from https://pytorch.org/audio/main/tutorials/squim_tutorial.html#sphx-glr-tutorials-squim-tutorial-py
6
6
  paper: https://arxiv.org/pdf/2304.01448.pdf
7
7
 
8
- needs
8
+ needs
9
9
  pip uninstall -y torch torchvision torchaudio
10
10
  pip install --pre torch torchvision torchaudio --extra-index-url https://download.pytorch.org/whl/nightly/cpu
11
11
 
@@ -1,4 +1,4 @@
1
- """ feats_snr.py is to estimate snr.
1
+ """feats_snr.py is to estimate snr.
2
2
 
3
3
  SNR (signal to noise ratio) is extracted as acoustic features.
4
4
  """
@@ -1,6 +1,6 @@
1
1
  """Extract acoustic features from audio samples.
2
2
 
3
- Extract acoustic features using several feature extractors
3
+ Extract acoustic features using several feature extractors
4
4
  (appends the features column-wise)
5
5
  """
6
6
 
@@ -75,7 +75,7 @@ class FeatureExtractor:
75
75
  return TRILLset
76
76
 
77
77
  elif feats_type.startswith(
78
- ("wav2vec2", "hubert", "wavlm", "spkrec", "whisper", "ast")
78
+ ("wav2vec2", "hubert", "wavlm", "spkrec", "whisper", "ast", "emotion2vec")
79
79
  ):
80
80
  return self._get_feat_extractor_by_prefix(feats_type)
81
81
 
nkululeko/models/model.py CHANGED
@@ -3,11 +3,15 @@ import ast
3
3
  import pickle
4
4
  import random
5
5
 
6
+ from joblib import parallel_backend
6
7
  import numpy as np
7
8
  import pandas as pd
9
+ from sklearn.model_selection import GridSearchCV
10
+ from sklearn.model_selection import LeaveOneGroupOut
11
+ from sklearn.model_selection import StratifiedKFold
8
12
  import sklearn.utils
9
- from joblib import parallel_backend
10
- from sklearn.model_selection import GridSearchCV, LeaveOneGroupOut, StratifiedKFold
13
+
14
+ import audeer
11
15
 
12
16
  import nkululeko.glob_conf as glob_conf
13
17
  from nkululeko.reporting.reporter import Reporter
@@ -301,8 +305,15 @@ class Model:
301
305
  def get_type(self):
302
306
  return "generic"
303
307
 
304
- def predict_sample(self, features):
305
- """Predict one sample"""
308
+ def predict_sample(self, features: np.ndarray) -> dict | float:
309
+ """Predict a single sample using the trained model.
310
+
311
+ Args:
312
+ features (np.ndarray): The feature vector of the sample to predict.
313
+
314
+ Returns:
315
+ dict: A dictionary containing the predicted class probabilities or value.
316
+ """
306
317
  prediction = {}
307
318
  if self.util.exp_is_classification():
308
319
  # get the class probabilities
@@ -336,3 +347,30 @@ class Model:
336
347
  self.set_id(run, epoch)
337
348
  with open(path, "rb") as handle:
338
349
  self.clf = pickle.load(handle)
350
+
351
+ # next function exports the model to onnx
352
+ def export_onnx(self, onnx_path, input_shape=None):
353
+ """Export the trained sklearn model to ONNX format.
354
+
355
+ Args:
356
+ onnx_path (str): Path to save the ONNX model.
357
+ input_shape (tuple, optional): Shape of the input features. If None, inferred from feats_train.
358
+ """
359
+ import skl2onnx
360
+ from skl2onnx import convert_sklearn
361
+ from skl2onnx.common.data_types import FloatTensorType
362
+
363
+ if not hasattr(self, "clf"):
364
+ self.util.error("No trained model found to export.")
365
+ return
366
+
367
+ if input_shape is None:
368
+ n_features = self.feats_train.shape[1]
369
+ initial_type = [("input", FloatTensorType([None, n_features]))]
370
+ else:
371
+ initial_type = [("input", FloatTensorType(input_shape))]
372
+
373
+ onnx_model = convert_sklearn(self.clf, initial_types=initial_type)
374
+ with open(audeer.path(onnx_path), "wb") as f:
375
+ f.write(onnx_model.SerializeToString())
376
+ self.util.debug(f"Model exported to ONNX at {onnx_path}")
@@ -1,4 +1,4 @@
1
- """
1
+ """
2
2
  model_cnn.py
3
3
 
4
4
  Inspired by code from Su Lei
@@ -1,4 +1,4 @@
1
- # xgbmodel.py
1
+ # model_xgb.py
2
2
 
3
3
  from xgboost import XGBClassifier
4
4
 
File without changes
@@ -0,0 +1,56 @@
1
+ import os
2
+
3
+ import numpy as np
4
+ import pandas as pd
5
+ import pytest
6
+
7
+ from nkululeko.models.model_svm import SVM_model
8
+
9
+
10
+ @pytest.fixture(scope="module")
11
+ def polish_data():
12
+ data_dir = os.path.abspath("data/polish")
13
+ train_csv = os.path.join(data_dir, "polish_train.csv")
14
+ test_csv = os.path.join(data_dir, "polish_test.csv")
15
+ # Load a small sample for speed
16
+ df_train = pd.read_csv(train_csv).head(10)
17
+ df_test = pd.read_csv(test_csv).head(5)
18
+ # Assume 'file' and 'emotion' columns exist
19
+ # Mock features: random floats, shape (n_samples, n_features)
20
+ feats_train = np.random.rand(len(df_train), 10)
21
+ feats_test = np.random.rand(len(df_test), 10)
22
+ return df_train, df_test, feats_train, feats_test
23
+
24
+
25
+ def test_svm_model_init(polish_data):
26
+ df_train, df_test, feats_train, feats_test = polish_data
27
+ model = SVM_model(df_train, df_test, feats_train, feats_test)
28
+ assert model.name == "svm"
29
+ assert hasattr(model, "clf")
30
+ assert model.is_classifier
31
+
32
+
33
+ def test_svm_model_fit_and_predict(polish_data):
34
+ df_train, df_test, feats_train, feats_test = polish_data
35
+ model = SVM_model(df_train, df_test, feats_train, feats_test)
36
+ # Fit the model
37
+ y_train = df_train["emotion"].astype(str)
38
+ model.clf.fit(feats_train, y_train)
39
+ # Predict
40
+ preds = model.clf.predict(feats_test)
41
+ assert len(preds) == feats_test.shape[0]
42
+
43
+
44
+ def test_svm_model_set_c(polish_data):
45
+ df_train, df_test, feats_train, feats_test = polish_data
46
+ model = SVM_model(df_train, df_test, feats_train, feats_test)
47
+ old_c = model.clf.C
48
+ model.set_c(2.0)
49
+ assert model.clf.C == 2.0
50
+ assert model.clf.C != old_c
51
+
52
+
53
+ def test_svm_model_get_type(polish_data):
54
+ df_train, df_test, feats_train, feats_test = polish_data
55
+ model = SVM_model(df_train, df_test, feats_train, feats_test)
56
+ assert model.get_type() == "svm"
nkululeko/nkululeko.py CHANGED
@@ -1,5 +1,7 @@
1
- # nkululeko.py
2
- # Entry script to do a Nkululeko experiment
1
+ #!/usr/bin/env python3
2
+
3
+ # nkululeko.py: Entry script to do a Nkululeko experiment
4
+
3
5
  import argparse
4
6
  import configparser
5
7
  from pathlib import Path
@@ -52,6 +54,15 @@ def doit(config_file):
52
54
  reports, last_epochs = expr.run()
53
55
  result = expr.get_best_report(reports).result.test
54
56
  expr.store_report()
57
+
58
+ # check if we want to export the model
59
+ o_path = util.config_val("EXP", "export_onnx", "False")
60
+ if eval(o_path):
61
+ print(f"Exporting ONNX model to {o_path}")
62
+ o_path = o_path.replace('"', '')
63
+ expr.runmgr.get_best_model().export_onnx(str(o_path))
64
+
65
+
55
66
  print("DONE")
56
67
  return result, int(np.asarray(last_epochs).min())
57
68
 
@@ -1,4 +1,4 @@
1
- """ reportitem.py
1
+ """reportitem.py
2
2
  a basic report snippet.
3
3
  """
4
4
 
nkululeko/runmanager.py CHANGED
@@ -1,6 +1,6 @@
1
1
  """Runmanager module.
2
2
 
3
- This module contains the Runmanager class which is responsible for managing the
3
+ This module contains the Runmanager class which is responsible for managing the
4
4
  runs of the experiment.
5
5
  """
6
6
 
@@ -22,8 +22,9 @@ class Runmanager:
22
22
  ) # The dataframes
23
23
  reports = []
24
24
 
25
- def __init__(self, df_train, df_test, feats_train,
26
- feats_test, dev_x=None, dev_y=None):
25
+ def __init__(
26
+ self, df_train, df_test, feats_train, feats_test, dev_x=None, dev_y=None
27
+ ):
27
28
  """Constructor setting up the dataframes.
28
29
 
29
30
  Args:
@@ -115,13 +116,23 @@ class Runmanager:
115
116
  + f"_BEST-dev_{best_report.run}_{best_report.epoch:03d}"
116
117
  )
117
118
  # finally, print out the numbers for this run
118
- self.print_report(best_report, plot_name)
119
+ # self.print_report(best_report, plot_name)
120
+ # remember the best run
121
+ # Only print if best_report is not the same as last_report
122
+ if best_report is not last_report:
123
+ plot_name = (
124
+ self.util.config_val("PLOT", "name", plot_name_suggest)
125
+ + f"_BEST-dev_{best_report.run}_{best_report.epoch:03d}"
126
+ )
127
+ self.print_report(best_report, plot_name)
128
+
119
129
  self.best_results.append(best_report)
120
130
  self.last_epochs.append(last_epoch)
121
131
  if self.split3:
122
132
  best_model = self.get_best_model()
123
133
  self.test_report = self.modelrunner.eval_specific_model(
124
- best_model, self.df_test, self.feats_test)
134
+ best_model, self.df_test, self.feats_test
135
+ )
125
136
  self.test_report.epoch = best_report.epoch
126
137
  plot_name = (
127
138
  self.util.config_val("PLOT", "name", plot_name_suggest)
@@ -170,12 +181,11 @@ class Runmanager:
170
181
  """
171
182
  # self.load_model(report)
172
183
  # report = self.model.predict()
173
- self.util.debug(f"plotting conf matrix to {plot_name}")
174
- report.plot_confmatrix(plot_name, epoch = report.epoch)
175
- report.print_results(report.epoch, file_name = plot_name)
184
+ self.util.debug(f"plotting conf matrix as {plot_name}")
185
+ report.plot_confmatrix(plot_name, epoch=report.epoch)
186
+ report.print_results(report.epoch, file_name=plot_name)
176
187
  report.print_probabilities(file_name=plot_name)
177
188
 
178
-
179
189
  def load_model(self, report):
180
190
  """Load a model from disk for a specific run and epoch and evaluate it.
181
191
 
nkululeko/scaler.py CHANGED
@@ -11,17 +11,24 @@ class Scaler:
11
11
  """Class to normalize speech features."""
12
12
 
13
13
  def __init__(
14
- self, train_data_df, test_data_df, train_feats, test_feats, scaler_type, dev_x = None, dev_y = None
14
+ self,
15
+ train_data_df,
16
+ test_data_df,
17
+ train_feats,
18
+ test_feats,
19
+ scaler_type,
20
+ dev_x=None,
21
+ dev_y=None,
15
22
  ):
16
23
  """Constructor.
17
24
 
18
- Parameters:
19
- train_data_df (pd.DataFrame): The training dataframe with speakers.
20
- only needed for speaker normalization
21
- test_data_df (pd.DataFrame): The test dataframe with speakers
22
- only needed for speaker normalization
23
- train_feats (pd.DataFrame): The train features dataframe
24
- test_feats (pd.DataFrame): The test features dataframe (can be None)
25
+ Parameters:
26
+ train_data_df (pd.DataFrame): The training dataframe with speakers.
27
+ only needed for speaker normalization
28
+ test_data_df (pd.DataFrame): The test dataframe with speakers
29
+ only needed for speaker normalization
30
+ train_feats (pd.DataFrame): The train features dataframe
31
+ test_feats (pd.DataFrame): The test features dataframe (can be None)
25
32
  """
26
33
  self.util = Util("scaler")
27
34
  if scaler_type == "standard":
@@ -45,12 +52,13 @@ class Scaler:
45
52
  else:
46
53
  self.feats_dev = None
47
54
  self.data_dev = None
55
+
48
56
  def scale(self):
49
57
  """Actually scales/normalizes.
50
58
 
51
- Returns:
52
- train_feats (pd.DataFrame): The scaled train features dataframe
53
- test_feats (pd.DataFrame): The scaled test features dataframe (can be None)
59
+ Returns:
60
+ train_feats (pd.DataFrame): The scaled train features dataframe
61
+ test_feats (pd.DataFrame): The scaled test features dataframe (can be None)
54
62
  """
55
63
  if self.scaler_type != "speaker":
56
64
  self.util.debug("scaling features based on training set")
@@ -66,7 +74,7 @@ class Scaler:
66
74
  if self.feats_test is not None:
67
75
  self.feats_test = self.scale_df(self.feats_test)
68
76
  if self.feats_dev is not None:
69
- self.feats_dev = self.scale_df(self.feats_dev)
77
+ self.feats_dev = self.scale_df(self.feats_dev)
70
78
  else:
71
79
  self.bin_to_three()
72
80
  if self.feats_dev is not None:
@@ -84,8 +92,8 @@ class Scaler:
84
92
  if self.feats_test is not None:
85
93
  self.feats_test = self.speaker_scale_df(self.data_test, self.feats_test)
86
94
  if self.feats_dev is not None:
87
- self.feats_dev = self.speaker_scale_df(self.data_dev, self.feats_dev)
88
- return [self.feats_train, self.feats_dev, self.feats_test]
95
+ self.feats_dev = self.speaker_scale_df(self.data_dev, self.feats_dev)
96
+ return [self.feats_train, self.feats_dev, self.feats_test]
89
97
  else:
90
98
  return [self.feats_train, self.feats_test]
91
99
 
@@ -1,6 +1,6 @@
1
1
  """test_predictor.py.
2
2
 
3
- Predict targets from a model and save as csv file.
3
+ Predict targets from a model and save as csv file.
4
4
 
5
5
  """
6
6
 
@@ -0,0 +1,38 @@
1
+ #!/usr/bin/env python3
2
+
3
+ # unzip.py - Extracts all files from the specified zip files (in case unzip is not installed).
4
+ # usage: python unzip.py file1.zip file2.zip ...
5
+ # source: https://askubuntu.com/questions/86849/how-to-unzip-a-zip-file-from-the-terminal
6
+
7
+ # mimics the unzip command
8
+ # # To extract an archive to a specific directory:
9
+ # unzip <archive>.zip -d <directory>
10
+
11
+ import argparse
12
+ from zipfile import ZipFile
13
+
14
+ # Set up argument parser
15
+ parser = argparse.ArgumentParser(description="Extract files from zip archives.")
16
+ parser.add_argument("zip_files", nargs="+", help="List of zip files to extract.")
17
+ parser.add_argument(
18
+ "-d",
19
+ "--directory",
20
+ default=".",
21
+ help="Directory to extract files to (default: current directory).",
22
+ )
23
+ args = parser.parse_args()
24
+
25
+ # Extract arguments
26
+ directory = args.directory
27
+ zip_files = args.zip_files
28
+
29
+ # Process each zip file
30
+ for zip_file in zip_files:
31
+ try:
32
+ with ZipFile(zip_file) as zf:
33
+ zf.extractall(path=directory)
34
+ print(f"Extracting {zip_file} to {directory}")
35
+ except FileNotFoundError:
36
+ print(f"Error: File {zip_file} not found")
37
+ except Exception as e:
38
+ print(f"Error extracting {zip_file}: {e}")
nkululeko/utils/util.py CHANGED
@@ -30,6 +30,7 @@ class Util:
30
30
  ]
31
31
 
32
32
  def __init__(self, caller=None, has_config=True):
33
+ self.logger = None
33
34
  if caller is not None:
34
35
  self.caller = caller
35
36
  else:
@@ -48,7 +49,12 @@ class Util:
48
49
  self.error(f"no such file: {self.got_data_roots}")
49
50
  self.data_roots = configparser.ConfigParser()
50
51
  self.data_roots.read(self.got_data_roots)
51
- except (ModuleNotFoundError, AttributeError):
52
+ except ModuleNotFoundError as e:
53
+ self.error(e)
54
+ self.config = None
55
+ self.got_data_roots = False
56
+ except AttributeError as e:
57
+ self.error(e)
52
58
  self.config = None
53
59
  self.got_data_roots = False
54
60
 
@@ -311,14 +317,22 @@ class Util:
311
317
  return False
312
318
 
313
319
  def error(self, message):
314
- self.logger.error(f"ERROR: {self.caller}: {message}")
320
+ if self.logger is not None:
321
+ self.logger.error(f"ERROR: {self.caller}: {message}")
322
+ else:
323
+ print(f"ERROR: {message}")
315
324
  sys.exit()
316
325
 
317
326
  def warn(self, message):
318
- self.logger.warning(f"WARNING: {self.caller}: {message}")
319
-
327
+ if self.logger is not None:
328
+ self.logger.warning(f"WARNING: {self.caller}: {message}")
329
+ else:
330
+ print(f"WARNING: {message}")
320
331
  def debug(self, message):
321
- self.logger.debug(f"DEBUG: {self.caller}: {message}")
332
+ if self.logger is not None:
333
+ self.logger.debug(f"DEBUG: {self.caller}: {message}")
334
+ else:
335
+ print(f"DEBUG: {message}")
322
336
 
323
337
  def set_config_val(self, section, key, value):
324
338
  try:
@@ -0,0 +1,76 @@
1
+ Metadata-Version: 2.4
2
+ Name: nkululeko
3
+ Version: 0.94.3
4
+ Summary: Machine learning audio prediction experiments based on templates
5
+ Home-page: https://github.com/felixbur/nkululeko
6
+ Author: Felix Burkhardt
7
+ Author-email: fxburk@gmail.com
8
+ Classifier: Programming Language :: Python :: 3
9
+ Classifier: License :: OSI Approved :: MIT License
10
+ Classifier: Operating System :: OS Independent
11
+ Classifier: Development Status :: 3 - Alpha
12
+ Classifier: Topic :: Scientific/Engineering
13
+ Requires-Python: >=3.9
14
+ License-File: LICENSE
15
+ Requires-Dist: audeer>=1.0.0
16
+ Requires-Dist: audformat>=1.3.1
17
+ Requires-Dist: audinterface>=1.0.0
18
+ Requires-Dist: audiofile>=1.0.0
19
+ Requires-Dist: audiomentations==0.31.0
20
+ Requires-Dist: audmetric>=1.0.0
21
+ Requires-Dist: audonnx>=0.7.0
22
+ Requires-Dist: confidence-intervals>=0.0.2
23
+ Requires-Dist: datasets>=2.0.0
24
+ Requires-Dist: imageio>=2.0.0
25
+ Requires-Dist: matplotlib>=3.0.0
26
+ Requires-Dist: numpy>=1.20.0
27
+ Requires-Dist: opensmile>=2.0.0
28
+ Requires-Dist: pandas>=1.0.0
29
+ Requires-Dist: praat-parselmouth>=0.4.0
30
+ Requires-Dist: scikit_learn>=1.0.0
31
+ Requires-Dist: scipy>=1.0.0
32
+ Requires-Dist: seaborn>=0.11.0
33
+ Requires-Dist: sounddevice>=0.4.0
34
+ Requires-Dist: transformers>=4.0.0
35
+ Requires-Dist: umap-learn>=0.5.0
36
+ Requires-Dist: xgboost>=1.0.0
37
+ Requires-Dist: pylatex>=1.0.0
38
+ Provides-Extra: torch
39
+ Requires-Dist: torch>=1.0.0; extra == "torch"
40
+ Requires-Dist: torchvision>=0.10.0; extra == "torch"
41
+ Requires-Dist: torchaudio>=0.10.0; extra == "torch"
42
+ Provides-Extra: torch-cpu
43
+ Requires-Dist: torch>=1.0.0; extra == "torch-cpu"
44
+ Requires-Dist: torchvision>=0.10.0; extra == "torch-cpu"
45
+ Requires-Dist: torchaudio>=0.10.0; extra == "torch-cpu"
46
+ Provides-Extra: torch-nightly
47
+ Requires-Dist: torch; extra == "torch-nightly"
48
+ Requires-Dist: torchvision; extra == "torch-nightly"
49
+ Requires-Dist: torchaudio; extra == "torch-nightly"
50
+ Provides-Extra: spotlight
51
+ Requires-Dist: renumics-spotlight>=1.6.13; extra == "spotlight"
52
+ Requires-Dist: sliceguard>=0.0.35; extra == "spotlight"
53
+ Provides-Extra: tensorflow
54
+ Requires-Dist: tensorflow>=2.0.0; extra == "tensorflow"
55
+ Requires-Dist: tensorflow_hub>=0.12.0; extra == "tensorflow"
56
+ Provides-Extra: all
57
+ Requires-Dist: torch>=1.0.0; extra == "all"
58
+ Requires-Dist: torchvision>=0.10.0; extra == "all"
59
+ Requires-Dist: torchaudio>=0.10.0; extra == "all"
60
+ Requires-Dist: renumics-spotlight>=0.1.0; extra == "all"
61
+ Requires-Dist: sliceguard>=0.1.0; extra == "all"
62
+ Requires-Dist: tensorflow>=2.0.0; extra == "all"
63
+ Requires-Dist: tensorflow_hub>=0.12.0; extra == "all"
64
+ Requires-Dist: shap>=0.40.0; extra == "all"
65
+ Requires-Dist: imblearn>=0.0.0; extra == "all"
66
+ Requires-Dist: cylimiter>=0.0.1; extra == "all"
67
+ Requires-Dist: audtorch>=0.0.1; extra == "all"
68
+ Requires-Dist: splitutils>=0.0.1; extra == "all"
69
+ Dynamic: author
70
+ Dynamic: author-email
71
+ Dynamic: home-page
72
+ Dynamic: license-file
73
+ Dynamic: provides-extra
74
+ Dynamic: requires-dist
75
+ Dynamic: requires-python
76
+ Dynamic: summary
@@ -1,17 +1,18 @@
1
+ examples/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
1
2
  nkululeko/__init__.py,sha256=62f8HiEzJ8rG2QlTFJXUCMpvuH3fKI33DoJSj33mscc,63
2
3
  nkululeko/aug_train.py,sha256=wpiHCJ7zsW38kumg3ypwXZe2HQrhUblAnv7P2QeJnAc,3525
3
4
  nkululeko/augment.py,sha256=3RzaxB3gRxovgJVjHXi0glprW01J7RaHhUkqotW2T3U,2955
4
5
  nkululeko/cacheddataset.py,sha256=XFpWZmbJRg0pvhnIgYf0TkclxllD-Fctu-Ol0PF_00c,969
5
- nkululeko/constants.py,sha256=4_cPNkLfZWa0md1LsHb3_P28dE2j0zAcBid8gDk0hsY,39
6
+ nkululeko/constants.py,sha256=KCqkmtwj--gcAdaRwj_Zb44_ewVNp06Hfp8-YGDG8iI,39
6
7
  nkululeko/demo-ft.py,sha256=iD9Pzp9QjyAv31q1cDZ75vPez7Ve8A4Cfukv5yfZdrQ,770
7
- nkululeko/demo.py,sha256=4Yzhg6pCPBYPGJrP7JX2TysVosl_R1llpVDKc2P_gUA,4955
8
+ nkululeko/demo.py,sha256=tu7Al2l5MCLVegkDC-NE2wcuc_YE7NRbgOlPW3yhGEs,4940
8
9
  nkululeko/demo_feats.py,sha256=BvZjeNFTlERIRlq34OHM4Z96jdDQAhB01BGQAUcX9dM,2026
9
10
  nkululeko/demo_predictor.py,sha256=lDF-xOxRdEAclOmbepAYg-BQXQdGkHfq2n74PTIoop8,4872
10
11
  nkululeko/ensemble.py,sha256=71V-rre61H3J4sh7lu-OTo4I2_g7mm_rQxwW1ARDHgY,12782
11
- nkululeko/experiment.py,sha256=ywswsCdSDUQLWIHn055wT1N40hFBSBUB3NnS5Hq6aMk,36210
12
+ nkululeko/experiment.py,sha256=xZQ3SpFhH4QByRzVBCO4Ps84KDXKuVPZ_qUzLUPgN5g,36221
12
13
  nkululeko/explore.py,sha256=FPM2CS-LKgcDV-LnjYlD6pEv7HuCQpH_C3KyyiOCdk4,3589
13
14
  nkululeko/export.py,sha256=U-V4acxtuL6qKt6oAsVcM5TTeWogYUJ3GU-lA6rq6d4,4336
14
- nkululeko/feature_extractor.py,sha256=UnspIWz3XrNhKnBBhWZkH2bHvD-sROtrQVqB1JvkUyw,4088
15
+ nkululeko/feature_extractor.py,sha256=X6ZWDjGwUMVwnP6TkCEnw8B4xo8eWvJa1QT9-0WUuvA,4102
15
16
  nkululeko/file_checker.py,sha256=xJY0Q6w47pnmgJVK5rcAKPYBrCpV7eBT4_3YBzTx-H8,3454
16
17
  nkululeko/filter_data.py,sha256=4sGrKvMZ_hLnJPrHm_CqjDPKIRV8REWoT7nfSYGXbwo,7305
17
18
  nkululeko/fixedsegment.py,sha256=Tb92QiuiyMsOO3WRWwuGjZGibS8hbHHCrcWAXGk7g04,2868
@@ -19,34 +20,34 @@ nkululeko/glob_conf.py,sha256=KL9YJQTHvTztxo1vr25qRRgaPnx4NTg0XrdbovKGMmw,525
19
20
  nkululeko/modelrunner.py,sha256=NpDgXfKkn8dOrQzhUiEfGI56Qrb1sOtWTD31II4Zgbk,11550
20
21
  nkululeko/multidb.py,sha256=sO6OwJn8sn1-C-ig3thsIL8QMWHdV9SnJhDodKjeKrI,6876
21
22
  nkululeko/nkuluflag.py,sha256=PGWSmZz-PiiHLgcZJAoGOI_Y-sZDVI1ksB8p5r7riWM,3725
22
- nkululeko/nkululeko.py,sha256=0RMce-dOyt7ldvo5pHGTL5R7H5NPPVklhMtRmWoZh1I,1952
23
+ nkululeko/nkululeko.py,sha256=FaLimlbx47rJgWgDEd0ZROAiXy2cOypliVdqJn-Bvws,2257
23
24
  nkululeko/plots.py,sha256=i9VIkviBWLgncfnyK44TUMzg2Xa0_UhfL0LnMF1vHTw,27022
24
25
  nkululeko/predict.py,sha256=MLnHEyFmSiHLLs-HDczag8Vu3zKF5T1rXLKdZZJ6py8,2083
25
26
  nkululeko/resample.py,sha256=rn3-M1A-iwVGibfQNGyeYNa7briD24lIN9Szq_1uTJo,5194
26
- nkululeko/runmanager.py,sha256=2jAUsWA5A13xTwEb4M3TmGLJsAUAZB2i4K41F6AAZYo,8478
27
- nkululeko/scaler.py,sha256=D3x4waIfTqt1vGBKd__uJslyss1kSNd9BUtj4_4eG_8,5105
27
+ nkululeko/runmanager.py,sha256=YtGQP0UyyQTKkilncB1XYM-T8oatzGcZEOcj5SorjJw,8902
28
+ nkululeko/scaler.py,sha256=a4lKwWT436TV4VEvqtP1uQ58Yz67XVHr1HjO5gp3xLI,5109
28
29
  nkululeko/segment.py,sha256=7UrJEwdLmh9wDL5iBwpdJyJm9dwSxidHrHt-_D2qtxw,4949
29
30
  nkululeko/syllable_nuclei.py,sha256=5w_naKxNxz66a_qLkraemi2fggM-gWesiiBPS47iFcE,9931
30
31
  nkululeko/test.py,sha256=1w624vo5KTzmFC8BUStGlLDmIEAFuJUz7J0W-gp7AxI,1677
31
- nkululeko/test_predictor.py,sha256=DEHE_D3A6m6KJTrpDKceA1n655t_UZV3WQd57K4a3Ho,2863
32
+ nkululeko/test_predictor.py,sha256=RPQxorj1uygLeSnAuNims5CFccXwrDwTnrIDs-gDlNQ,2859
32
33
  nkululeko/test_pretrain.py,sha256=6FZeETlWzg9Cq_sn3BFKhfH91jW26nAIDm1bJkInNNA,8463
33
34
  nkululeko/augmenting/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
34
35
  nkululeko/augmenting/augmenter.py,sha256=TUUznEz0pe9DSMC9r7LoBckuvsJTprvypeV5-8zLn20,2846
35
- nkululeko/augmenting/randomsplicer.py,sha256=TKPqp8np5dvyJIAjOTvtlanatFQ9OwKxZ02QoCwZ2Jw,2802
36
- nkululeko/augmenting/randomsplicing.py,sha256=RUwYukqDUbRqs_hD2wYPL6g2nLFhjCuPVbJ6qx3VzU8,1751
37
- nkululeko/augmenting/resampler.py,sha256=gcjyyTD6QtJK6s_xoOQpsu5adpn0uSJwHxJTHMskfOM,3541
36
+ nkululeko/augmenting/randomsplicer.py,sha256=TQTy4RBt6XbWiuUu5Ic913DMvmwTUwEufldBJjo7i1s,2801
37
+ nkululeko/augmenting/randomsplicing.py,sha256=GXCpCDdOsOyWACDJ3ujmFZBVe6ISvkoQLefBNPgxxow,1750
38
+ nkululeko/augmenting/resampler.py,sha256=j2yuB9h9UwGQHqwF8CZPSGqAfOiyQV3979WQjU2toVM,3962
38
39
  nkululeko/autopredict/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
39
- nkululeko/autopredict/ap_age.py,sha256=SaD8-WWBLjb4x2jxIsU-_uvlYxcE0YhxUOnh9PAYTiU,1097
40
- nkululeko/autopredict/ap_arousal.py,sha256=unKN9VefJ_eesUqy1YTMSvYs1kBMQP1HBZI6cY0En6c,1026
40
+ nkululeko/autopredict/ap_age.py,sha256=yzd8sF6gi0hnqNawyLBCIkt-pKgl9gYPlZHsrLGfz0U,1098
41
+ nkululeko/autopredict/ap_arousal.py,sha256=lpv3jTSVEVCcR226JevNM6S7e0_uMZXHb_8Wpup1yj8,1027
41
42
  nkululeko/autopredict/ap_dominance.py,sha256=Ltq5x0ralxU1758_e-nNKvzexiPUM66xLAm3Wo2B07c,1040
42
- nkululeko/autopredict/ap_gender.py,sha256=b6oTqHKVwOnYh4YlKbuMflssS4HJqs_c1ayusauY_I4,1010
43
- nkululeko/autopredict/ap_mos.py,sha256=e4hmgb0Yf1_AbC5P0CqXJIvufjhbTrqmI5goARxrY0Y,1107
44
- nkululeko/autopredict/ap_pesq.py,sha256=mRt3Loucaoy4vJxwfuxUt0fP88bMGvkmrLCEpKEXWp0,1140
45
- nkululeko/autopredict/ap_sdr.py,sha256=VQ2UkxOO3ipqYNNjFwKgEaGCk8IzLI5lX_2tZFLIvTY,1188
46
- nkululeko/autopredict/ap_sid.py,sha256=mCxf2DUOPUlDdnVwCeljFJtCXM4uum1poZQ9RrwHHM8,2641
47
- nkululeko/autopredict/ap_snr.py,sha256=AiTU8-7CMEeowmYkMO19lw1HCb1yTXC6KeulNf8gOqw,1110
48
- nkululeko/autopredict/ap_stoi.py,sha256=UEQg1ZV0meAsxgdWB8ieRs9GPXHqArmsaOyCGRwpcnA,1187
49
- nkululeko/autopredict/ap_valence.py,sha256=WrW4Ltqi_odW49_4QEVKkfnrcztLIVZ4cXIEHu4dBN8,1026
43
+ nkululeko/autopredict/ap_gender.py,sha256=RjLv9YxY9OPHT_gnd6htjKQzQA4DSKcbjipKGjHHx2A,1011
44
+ nkululeko/autopredict/ap_mos.py,sha256=PMLU67JDgYQMobRSR2vW9cWoL3QK5JbhLM65fVsRGkc,1108
45
+ nkululeko/autopredict/ap_pesq.py,sha256=EuJ9u6oaSPWdYsaU8q3t8tiFKhfW1qdqgO-cySpfxw0,1141
46
+ nkululeko/autopredict/ap_sdr.py,sha256=xYCy4M_aWzoFiYD_KOK9ys2P2v0bfxNkLcIRdi5z2h4,1188
47
+ nkululeko/autopredict/ap_sid.py,sha256=b_JwVWlqcwdC7acU9Q7mExuOJKUn6qdlmQTm8pmmptk,2642
48
+ nkululeko/autopredict/ap_snr.py,sha256=cjc0pUsCN_RacTw1UBR2cGY9t_um48f2cjo3QJDn7bw,1111
49
+ nkululeko/autopredict/ap_stoi.py,sha256=csv9qCcRmieHAhypszqGoGt9r3biM8IYPgcTwp9GIFM,1188
50
+ nkululeko/autopredict/ap_valence.py,sha256=9S06SpO_zXKSpkf0InHYYXZcD9HDGoCJ6UPkn__eBAg,1027
50
51
  nkululeko/autopredict/estimate_snr.py,sha256=1k9-XadABudnsNOeFZD_Fg0E64-GUQVS7JEp82MLQS4,4995
51
52
  nkululeko/data/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
52
53
  nkululeko/data/dataset.py,sha256=JLbBYGniUrjwxs-HtbIyhqO3Cv-ELfpmlq7jzij4dBc,41759
@@ -59,15 +60,16 @@ nkululeko/feat_extract/feats_ast.py,sha256=w62xEoLiFtU-rj6SXkqXAktmoFaXcAcAWpUyE
59
60
  nkululeko/feat_extract/feats_auddim.py,sha256=CGLp_aYhudfwoU5522vjrvjPxfZcyw593A8xLjYefV8,3134
60
61
  nkululeko/feat_extract/feats_audmodel.py,sha256=OsZyB1rdcG0Fai2gAwBlbuubmWor1_-P4IDkZLqgPKE,3161
61
62
  nkululeko/feat_extract/feats_clap.py,sha256=1tttpfm2SJmQgYm2u8eUVpDiDOpWdKqFChpY3ZZokNs,3395
63
+ nkululeko/feat_extract/feats_emotion2vec.py,sha256=ObVlqbsJsw-hWGsUOXY68Ebynt5Bn4Xtlu_Gvq3XJI4,8728
62
64
  nkululeko/feat_extract/feats_hubert.py,sha256=F3vrPCkx8EimJjFWYCZ7Yg9uo1G3NjYt4UKrGIUev8k,5172
63
65
  nkululeko/feat_extract/feats_import.py,sha256=cPi4XRuRs71npB8YGXr7rYOvkeTU_oZEl3GrGncdiqY,2222
64
66
  nkululeko/feat_extract/feats_mld.py,sha256=5aRoYiGDm5ApoFntxAMQYPjEelXHHRBHZcAJR9dxaeI,1945
65
- nkululeko/feat_extract/feats_mos.py,sha256=3UXCKe86F49yHpZMQnLfDWXx9XdmlXHOy8efoa3WaOk,4138
67
+ nkululeko/feat_extract/feats_mos.py,sha256=vkH1FdXtduoU0-yjBtVccC2b_p_eyH8laRnwlL7QTVM,4136
66
68
  nkululeko/feat_extract/feats_opensmile copy.py,sha256=BLj5sUaBPz7vLPfNlt9LdQurSypmViqgSpPK-6aXGhQ,4029
67
69
  nkululeko/feat_extract/feats_opensmile.py,sha256=HwbGs0EaPxZ7DznQZFem8RYgyQWz02oya77uVY7KhZE,9203
68
70
  nkululeko/feat_extract/feats_oxbow.py,sha256=TRoEJx5EKZiqoPoPRibHc0vkBMoZcKlGoGNq4NbyHZw,4895
69
71
  nkululeko/feat_extract/feats_praat.py,sha256=jZ-XXbP3iy25QQIzA4Hrv0HxsYvJNPavoCW2FyJNKMg,3064
70
- nkululeko/feat_extract/feats_snr.py,sha256=5uEm10d89TQPf0s-CuVpQ3ftc0bLEeuB8aGuufsjAbs,2762
72
+ nkululeko/feat_extract/feats_snr.py,sha256=Zxwo78HLleNsziYLOj34RQUnp9I7r1yMXqjYipDOjZw,2761
71
73
  nkululeko/feat_extract/feats_spectra.py,sha256=6WhFUpB0WTutg7OFMlAw9lSwVU5OBYCDcPRxaiH-Qn8,3621
72
74
  nkululeko/feat_extract/feats_spkrec.py,sha256=o_6bdU4lIkj64S5Kdjf1iyuo1VASeYxE4XdxV94a8gE,4732
73
75
  nkululeko/feat_extract/feats_squim.py,sha256=yJifsp9kj9iJjW_UAKr3LlvVhX5rv7el4bepn0wN2a8,4578
@@ -82,9 +84,9 @@ nkululeko/losses/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,
82
84
  nkululeko/losses/loss_ccc.py,sha256=NOK0y0fxKUnU161B5geap6Fmn8QzoPl2MqtPiV8IuJE,976
83
85
  nkululeko/losses/loss_softf1loss.py,sha256=5gW-PuiqeAZcRgfwjueIOQtMokOjZWgQnVIv59HKTCo,1309
84
86
  nkululeko/models/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
85
- nkululeko/models/model.py,sha256=2STBD3jtLKeNSk7arCFJdaV6FL-nuLR1qpsjvZ4W-9A,12975
87
+ nkululeko/models/model.py,sha256=0O6H-kME1yVHU-EKu5iOZVBB7fFNg3lfagvGgMrldxM,14426
86
88
  nkululeko/models/model_bayes.py,sha256=tQUXEsXoS6WnfapQjP78S_gxNBssTOqE78A2iG8SfLU,407
87
- nkululeko/models/model_cnn.py,sha256=lu6ZSGqJBL69PdrgwwgzjGmu_DaBaiATkz6oVqQpKhc,10498
89
+ nkululeko/models/model_cnn.py,sha256=TKj43865epsiK7a0COyfBDaFHKOYgWgnPpMVCPWUhCM,10497
88
90
  nkululeko/models/model_gmm.py,sha256=mhHFNtTzHuJvqYSA0h5YhvjA--KhnN6MTU_S0G3-d1c,1332
89
91
  nkululeko/models/model_knn.py,sha256=ByQlHIU_fNtSCGCvsrMEoLVJ9q2hUC4edtpp5rVS1B8,600
90
92
  nkululeko/models/model_knn_reg.py,sha256=kaVP1xGNgktUGuQARi7uoJ0hmdPGHDpv2ugDesYN7RU,611
@@ -96,13 +98,15 @@ nkululeko/models/model_svr.py,sha256=FEwYRdgqwgGhZdkpRnT7Ef12lklWi6GZL28PyV99xWs
96
98
  nkululeko/models/model_tree.py,sha256=6L3PD3aIiiQz1RPWS6z3Edx4f0gnR7AOfBKOJzf0BNU,433
97
99
  nkululeko/models/model_tree_reg.py,sha256=IMaQpNImoRqP8Biw1CsJevxpV_PVpKblsKtYlMW5d_U,429
98
100
  nkululeko/models/model_tuned.py,sha256=VuRyNqw3XTpQ2eHsWOJN8X-V98AN8Wqiq7UgwT5BQRU,23763
99
- nkululeko/models/model_xgb.py,sha256=ytBaSHZH8r7VvRYdmrBrQnzRM6V4HyCJ8O-v20J8G_g,448
101
+ nkululeko/models/model_xgb.py,sha256=zfZM3lqH5uttVB18b1MRIhP9CCeCuIh1ycgOuFMcqUM,449
100
102
  nkululeko/models/model_xgr.py,sha256=H01FJCRgmX2unvambMs5TTCS9sI6VDB9ip9G6rVGt2c,419
103
+ nkululeko/models/tests/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
104
+ nkululeko/models/tests/test_model_svm.py,sha256=spDlZmeBKBdK4EFBpOgEkaAfGeGH9kau6CqSWOY6Uag,1856
101
105
  nkululeko/reporting/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
102
106
  nkululeko/reporting/defines.py,sha256=0vh-Tlx4fAPpk1o6mP_4x3EkIoqzYMr38IZnj-JM5z4,641
103
107
  nkululeko/reporting/latex_writer.py,sha256=NGwSIfd4nfslDkNUOSZSdqY_VDLA8634thyhe-vj1bY,1824
104
108
  nkululeko/reporting/report.py,sha256=bYN8B66gg3IWHAyfd6uIVjpYKy3rOI6aEwgfXU0LSAY,1006
105
- nkululeko/reporting/report_item.py,sha256=AqKD40AlZpRuHLbggn5PkH6ctGJwh9rGNBNgOvgUODg,534
109
+ nkululeko/reporting/report_item.py,sha256=drkknsyFhGviaPJNmPQtCXJmRhTSSfjNcJt0Bls6JAA,533
106
110
  nkululeko/reporting/reporter.py,sha256=-VyV0TZ0vBAx6UZNegnKS3i3WpkF27ntBRlYvp9NNiQ,20174
107
111
  nkululeko/reporting/result.py,sha256=G63a2tHCwHhM6NBJgYzsWKWJm4Yu3r4hsCHA2Km7eHU,1073
108
112
  nkululeko/segmenting/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
@@ -112,10 +116,11 @@ nkululeko/segmenting/seg_silero.py,sha256=ulodnvtRq5MLHDxy_RmAK4tJg6h1d-mPq-uCPF
112
116
  nkululeko/utils/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
113
117
  nkululeko/utils/files.py,sha256=SrrYaU7AB80MZHiV1jcB0h_zigvYLYgSVNTXV4ao38g,4593
114
118
  nkululeko/utils/stats.py,sha256=3Fyx8q8BSKYmiufT6OkRug9RATWmGrr9BaX_y8jziWo,3074
115
- nkululeko/utils/util.py,sha256=nZJtWqzFx3Zdp6Pve_ZAbb01yRTpIsgBXnoPy1VgtRE,17356
116
- nkululeko-0.94.1.dist-info/licenses/LICENSE,sha256=0zGP5B_W35yAcGfHPS18Q2B8UhvLRY3dQq1MhpsJU_U,1076
117
- nkululeko-0.94.1.dist-info/METADATA,sha256=JoeRpOcdclL11EV6vPNmw9gvmlm8VOO8yaoETjs2k-M,1169
118
- nkululeko-0.94.1.dist-info/WHEEL,sha256=CmyFI0kx5cdEMTLiONQRbGQwjIoR1aIYB7eCAQ4KPJ0,91
119
- nkululeko-0.94.1.dist-info/entry_points.txt,sha256=lNTkFEdh6Kjo5o95ZAWf_0Lq-4ztGoAoMVSDuPtuyS0,442
120
- nkululeko-0.94.1.dist-info/top_level.txt,sha256=DPFNNSHPjUeVKj44dVANAjuVGRCC3MusJ08lc2a8xFA,10
121
- nkululeko-0.94.1.dist-info/RECORD,,
119
+ nkululeko/utils/unzip.py,sha256=G68f5120TjwACZC3bQcneMniddnwubPbBdMc2L5KBOo,1206
120
+ nkululeko/utils/util.py,sha256=6NDKhOx0fV5fKyhSoY4hem96p7OuPcmhCDQR9EzkQhw,17829
121
+ nkululeko-0.94.3.dist-info/licenses/LICENSE,sha256=0zGP5B_W35yAcGfHPS18Q2B8UhvLRY3dQq1MhpsJU_U,1076
122
+ nkululeko-0.94.3.dist-info/METADATA,sha256=QeZ9ZMTqwgdDvwRTCvgFO7X55_J84AWZh7jVf9uV-6M,2874
123
+ nkululeko-0.94.3.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
124
+ nkululeko-0.94.3.dist-info/entry_points.txt,sha256=lNTkFEdh6Kjo5o95ZAWf_0Lq-4ztGoAoMVSDuPtuyS0,442
125
+ nkululeko-0.94.3.dist-info/top_level.txt,sha256=bf1k1YKkqcXemNX_cUgoyKqQ3_GVErPqAY-53J36jkM,19
126
+ nkululeko-0.94.3.dist-info/RECORD,,
@@ -1,5 +1,5 @@
1
1
  Wheel-Version: 1.0
2
- Generator: setuptools (78.1.0)
2
+ Generator: setuptools (80.9.0)
3
3
  Root-Is-Purelib: true
4
4
  Tag: py3-none-any
5
5
 
@@ -1,40 +0,0 @@
1
- Metadata-Version: 2.4
2
- Name: nkululeko
3
- Version: 0.94.1
4
- Summary: Machine learning audio prediction experiments based on templates
5
- Home-page: https://github.com/felixbur/nkululeko
6
- Author: Felix Burkhardt
7
- Author-email: fxburk@gmail.com
8
- Classifier: Programming Language :: Python :: 3
9
- Classifier: License :: OSI Approved :: MIT License
10
- Classifier: Operating System :: OS Independent
11
- Classifier: Development Status :: 3 - Alpha
12
- Classifier: Topic :: Scientific/Engineering
13
- Requires-Python: >=3.9
14
- License-File: LICENSE
15
- Requires-Dist: audeer
16
- Requires-Dist: audformat
17
- Requires-Dist: audinterface
18
- Requires-Dist: audiofile
19
- Requires-Dist: audiomentations
20
- Requires-Dist: audmetric
21
- Requires-Dist: audonnx
22
- Requires-Dist: confidence_intervals
23
- Requires-Dist: datasets
24
- Requires-Dist: imageio
25
- Requires-Dist: matplotlib
26
- Requires-Dist: numpy
27
- Requires-Dist: opensmile
28
- Requires-Dist: pandas
29
- Requires-Dist: praat-parselmouth
30
- Requires-Dist: scikit_learn
31
- Requires-Dist: scipy
32
- Requires-Dist: seaborn
33
- Requires-Dist: sounddevice
34
- Requires-Dist: torch
35
- Requires-Dist: torchvision
36
- Requires-Dist: transformers
37
- Requires-Dist: umap-learn
38
- Requires-Dist: xgboost
39
- Requires-Dist: pylatex
40
- Dynamic: license-file