e@0
|
1 # -*- coding: utf-8 -*-
|
e@0
|
2 """
|
e@0
|
3 Created on Mon Jun 1 11:42:06 2015
|
e@0
|
4
|
e@0
|
5 @author: Emmanouil Theofanis Chourdakis
|
e@0
|
6 """
|
e@0
|
7
|
e@0
|
8 # Note, reference everything!
|
e@0
|
9
|
e@0
|
10 from sys import argv
|
e@0
|
11
|
e@0
|
12
|
e@0
|
13 if __name__=="__main__":
|
e@0
|
14 if len(argv) != 3:
|
e@0
|
15 print("Incorrect number of arguments:")
|
e@0
|
16 print("Usage: ")
|
e@0
|
17 print("%s <input> <output>")
|
e@0
|
18 print("")
|
e@0
|
19 print("Arguments:")
|
e@0
|
20 print("<input>\tThe input filename. Can be .wav, .mp3, etc...")
|
e@0
|
21 print("<parameters>\t The parameters filename, in .yaml format" )
|
e@0
|
22 print("<output>\tThe output filename in .yaml format")
|
e@0
|
23 sys.exit(-1)
|
e@0
|
24 else:
|
e@0
|
25
|
e@0
|
26 print("[II] Loading libraries")
|
e@0
|
27
|
e@0
|
28 import essentia
|
e@0
|
29 from essentia import Pool
|
e@0
|
30 from essentia.standard import *
|
e@0
|
31 import yaml
|
e@0
|
32
|
e@0
|
33
|
e@0
|
34 # reqyures matplotlib
|
e@0
|
35 from pylab import *
|
e@0
|
36
|
e@0
|
37 #requires numpy
|
e@0
|
38 from numpy import *
|
e@0
|
39
|
e@0
|
40 #requires scikit-learn
|
e@0
|
41 from sklearn.metrics import pairwise_distances
|
e@0
|
42
|
e@0
|
43 d = {}
|
e@0
|
44 v = {}
|
e@0
|
45
|
e@0
|
46 fname = argv[1]
|
e@0
|
47 outfname = argv[2]
|
e@0
|
48
|
e@0
|
49
|
e@0
|
50
|
e@0
|
51 trackname = fname.split('.')[0].split('/')[-1]
|
e@0
|
52
|
e@0
|
53
|
e@0
|
54 if outfname.partition('.')[-1].lower() not in ['json', 'yaml']:
|
e@0
|
55 print("Please choose a .json or .yaml as an output file.")
|
e@0
|
56 sys.exit(-1)
|
e@0
|
57 else:
|
e@0
|
58 if outfname.partition('.')[-1].lower() == 'json':
|
e@0
|
59 output = YamlOutput(filename = outfname, format='json')
|
e@0
|
60 else:
|
e@0
|
61 output = YamlOutput(filename = outfname, format='yaml')
|
e@0
|
62
|
e@0
|
63 print("Feature extraction of `%s\'" % fname)
|
e@0
|
64
|
e@0
|
65 # Sampling Rate
|
e@0
|
66 SR = 16000.0
|
e@0
|
67
|
e@0
|
68 # Sampling Frequency
|
e@0
|
69 T = 1.0/SR
|
e@0
|
70
|
e@0
|
71 # FrameSize
|
e@0
|
72 tframeSize = 23 #ms
|
e@0
|
73 frameSize = int(ceil(tframeSize*SR/1000)) if mod(ceil(tframeSize*SR/1000),2) == 0 \
|
e@0
|
74 else int(floor(tframeSize*SR/1000))
|
e@0
|
75
|
e@0
|
76 # HopSize
|
e@0
|
77 hopSize = frameSize/2
|
e@0
|
78
|
e@0
|
79 # Load Audio
|
e@0
|
80 audio = MonoLoader(filename = fname, sampleRate=SR)()
|
e@0
|
81
|
e@0
|
82
|
e@0
|
83 #Window Frames
|
e@0
|
84 w = Windowing(size = frameSize, type = 'hamming')
|
e@0
|
85
|
e@0
|
86 # Spectrum
|
e@0
|
87 spec = Spectrum(size=1024)
|
e@0
|
88
|
e@0
|
89 # Pool to append mean and variance
|
e@0
|
90 pool = Pool()
|
e@0
|
91 globalPool = Pool()
|
e@0
|
92
|
e@0
|
93 # Below are Features to be used in the feature extraction stage
|
e@0
|
94 # We use, Spectral Contrast, MFCCs, Zero-Crossing rate, RMS,
|
e@0
|
95 # Crest Factor, Spectral Centroid, Spectral Occupation, Spectral Flux
|
e@0
|
96
|
e@0
|
97 # Spectral Contrast
|
e@0
|
98 sc = SpectralContrast(frameSize = frameSize, highFrequencyBound = 8000, sampleRate = SR)
|
e@0
|
99
|
e@0
|
100 # MFCCs
|
e@0
|
101 mfccs = MFCC(highFrequencyBound = 8000, sampleRate = SR)
|
e@0
|
102
|
e@0
|
103 # Spectral Centroid
|
e@0
|
104 centroid = Centroid(range = SR/2)
|
e@0
|
105
|
e@0
|
106 # Spectral Roll-Off
|
e@0
|
107 rolloff = RollOff(sampleRate = SR, cutoff = 0.9)
|
e@0
|
108
|
e@0
|
109 # Spectral Flux
|
e@0
|
110 flux = Flux()
|
e@0
|
111
|
e@0
|
112 # Zero Crossing Rate
|
e@0
|
113 zcr = ZeroCrossingRate()
|
e@0
|
114
|
e@0
|
115 # RMS
|
e@0
|
116 rms = RMS()
|
e@0
|
117
|
e@0
|
118 # Crest Factor
|
e@0
|
119 crest = Crest()
|
e@0
|
120
|
e@0
|
121
|
e@0
|
122
|
e@0
|
123
|
e@0
|
124 # Segmentation based on Onset detection-based temporal modeling
|
e@0
|
125 print("[II] Calculating features for %s, please wait..." % fname)
|
e@0
|
126 # Onset Detection
|
e@0
|
127
|
e@0
|
128 print("[II] Splitting to onsets...")
|
e@0
|
129
|
e@0
|
130 onsetdetection = OnsetDetectionGlobal(frameSize = frameSize, hopSize = hopSize, sampleRate = SR)(audio)
|
e@0
|
131 onsets = Onsets()(essentia.array([onsetdetection]), [1])
|
e@0
|
132
|
e@0
|
133
|
e@0
|
134
|
e@0
|
135 print("[II] done, extracting features...")
|
e@0
|
136 for o in range(0, len(onsets)-1):
|
e@0
|
137 IOI = audio[onsets[o]*SR:onsets[o+1]*SR]
|
e@0
|
138
|
e@0
|
139
|
e@0
|
140
|
e@0
|
141
|
e@0
|
142 if len(IOI) == 0:
|
e@0
|
143 break;
|
e@0
|
144
|
e@0
|
145
|
e@0
|
146 for frame in FrameGenerator(IOI, frameSize, hopSize):
|
e@0
|
147 # Temporal Features
|
e@0
|
148
|
e@0
|
149 zerocrossingrate = zcr(frame)
|
e@0
|
150 rmsvalues = rms(frame)
|
e@0
|
151
|
e@0
|
152 # Spectral features
|
e@0
|
153 framespectrum = spec(w(frame))
|
e@0
|
154 framecontrast = sc(framespectrum)
|
e@0
|
155 mfcc_coeffs = mfccs(framespectrum)[1]
|
e@0
|
156 spectralcentroid = centroid(framespectrum)
|
e@0
|
157 spectralrolloff = rolloff(framespectrum)
|
e@0
|
158 spectralflux = rolloff(framespectrum)
|
e@0
|
159
|
e@0
|
160
|
e@0
|
161
|
e@0
|
162 pool.add('lowlevel.zcr', zerocrossingrate)
|
e@0
|
163 pool.add('lowlevel.rms', rmsvalues)
|
e@0
|
164 pool.add('lowlevel.spectrum.centroid', spectralcentroid)
|
e@0
|
165 pool.add('lowlevel.spectrum.rolloff', spectralrolloff)
|
e@0
|
166 pool.add('lowlevel.mfcc.coeffs', mfcc_coeffs)
|
e@0
|
167 pool.add('lowlevel.spectrum.magnitude', framespectrum)
|
e@0
|
168 pool.add('lowlevel.contrast.contrast', framecontrast[0])
|
e@0
|
169 pool.add('lowlevel.contrast.valleys', framecontrast[1])
|
e@0
|
170 pool.add('lowlevel.spectrum.flux', spectralflux)
|
e@0
|
171
|
e@0
|
172
|
e@0
|
173
|
e@0
|
174 spectrumfull = pool['lowlevel.spectrum.magnitude']
|
e@0
|
175 spectralcontrast = pool['lowlevel.contrast.contrast']
|
e@0
|
176 spectralvalleys = pool['lowlevel.contrast.valleys']
|
e@0
|
177 spectralcentroidfeature = pool['lowlevel.spectrum.centroid']
|
e@0
|
178 spectralrollofffeature = pool['lowlevel.spectrum.rolloff']
|
e@0
|
179 spectralfluxfeature = pool['lowlevel.spectrum.flux']
|
e@0
|
180
|
e@0
|
181 spectralfeature = concatenate((spectralcontrast,spectralvalleys),1)
|
e@0
|
182 mfccfeature = pool['lowlevel.mfcc.coeffs']
|
e@0
|
183 zcrfeature = pool['lowlevel.zcr']
|
e@0
|
184 rmsfeature = pool['lowlevel.rms']
|
e@0
|
185 crestfeature = crest(rmsfeature)
|
e@0
|
186 1
|
e@0
|
187
|
e@0
|
188 meanspectralfeature = mean(spectralfeature, 0)
|
e@0
|
189 for i in range(0, shape(spectralfeature)[1]):
|
e@0
|
190 globalPool.add('spectralcontrast_%d' % i , meanspectralfeature[i])
|
e@0
|
191 globalPool.add('spectralcentroid', mean(spectralcentroidfeature, 0))
|
e@0
|
192 globalPool.add('spectralrolloff', mean(spectralrollofffeature, 0))
|
e@0
|
193 globalPool.add('spectralflux', mean(spectralfluxfeature, 0))
|
e@0
|
194
|
e@0
|
195 # Expand mfccs
|
e@0
|
196 meanmfcc = mean(mfccfeature, 0)
|
e@0
|
197 for i in range(0, shape(mfccfeature)[1]):
|
e@0
|
198 globalPool.add('mfcc_%d' % i, meanmfcc[i])
|
e@0
|
199
|
e@0
|
200
|
e@0
|
201 globalPool.add('zcr', mean(zcrfeature, 0))
|
e@0
|
202 globalPool.add('rms', mean(rmsfeature, 0))
|
e@0
|
203 globalPool.add('crest', crestfeature)
|
e@0
|
204
|
e@0
|
205 pool.clear()
|
e@0
|
206
|
e@0
|
207 print("[II] done.")
|
e@0
|
208
|
e@0
|
209
|
e@0
|
210 print("[II] Saving data to %s:" % outfname)
|
e@0
|
211 globalPool.add("metadata.filename", fname)
|
e@0
|
212 output(globalPool)
|
e@0
|
213
|
e@0
|
214
|