public static Matrix ShortTimeFourierTransform(Complex[] waveFragment, int hashSize, string fmt = "MIDI") { Console.Write($"\r\nBuilding a new MIDI model...\r\n"); var Model = new Matrix(hashSize); double Xmin = double.MaxValue, Xmax = double.MinValue, cc = 0; foreach (var fft in Complex.ShortTimeFourierTransform(waveFragment)) { int t = Model.Count; if (t >= Model.Length) { throw new OutOfMemoryException(); } var vec = Model[t] = CreateMidiVector(fft); for (var j = 0; j < vec.Axis.Length; j++) { Xmin = Math.Min(Xmin, vec.Axis[j].Re); Xmax = Math.Max(Xmax, vec.Axis[j].Re); } cc++; } for (int t = 0; t < Model.Length; t++) { if (Model[t] == null) { continue; } var vec = Model[t]; for (var j = 0; j < vec.Axis.Length; j++) { vec.Axis[j].Re = (vec.Axis[j].Re - Xmin) / (Xmax - Xmin); if (vec.Axis[j].Re <= 0.007) { vec.Axis[j].Re = 0; } RunSpeachFrequencyFilters( vec, j); } } var dBmax = int.MinValue; for (int t = 0; t < Model.Length; t++) { if (Model[t] == null) { continue; } var vec = Model[t]; for (var j = 0; j < vec.Axis.Length; j++) { vec.Axis[j].Re = Math.Round( (vec.Axis[j].Re - Xmin) / (Xmax - Xmin), 4); if (vec.Axis[j].Re > 0 && vec.Axis[j].Re < 1E-4) { vec.Axis[j].Re = 0; } RunSpeachFrequencyFilters( vec, j); if (vec.Axis[j].Re > 0) { var dB = Envelopes.AmplitudeTodB(vec.Axis[j].Re); if (dB > dBmax) { dBmax = dB; } } } } if (dBmax == int.MinValue) { dBmax = 0; } for (int t = 0; t < Model.Length; t++) { if (Model[t] == null) { continue; } var vec = Model[t]; for (var j = 0; j < vec.Axis.Length; j++) { if (vec.Axis[j].Re > 0) { var dB = Envelopes.AmplitudeTodB(vec.Axis[j].Re); vec.Axis[j].Re = Envelopes.dBToAmplitude(dB); } } } return(Model); }