def __init__(self, fl=1200, fs=240, fftl=2048): self.fl = fl self.fs = fs self.fftl = fftl winpower = np.sqrt(np.sum(np.square(np.blackman(self.fl).astype(np.float32)))) self.window = {'ana' : np.blackman(self.fl).astype(np.float32) / winpower, 'syn' : winpower / 0.42 / (self.fl / self.fs)}
def applyWindow(self, window="hanning", ww=0, cf=0): ''' Apply window function to frequency domain data cf: the frequency the window is centered over [Hz] ww: the window width [Hz], if ww equals 0 the window covers the full range ''' self.info("Applying %s window ..." % window) if window == "hanning": if ww == 0: w = np.hanning(self.numfreq) else: pos = int((cf - self.lowF) / self.deltaF) halfwidth = int(ww / (2.0 * self.deltaF)) w = np.zeros(self.numfreq) w[pos - halfwidth:pos + halfwidth] = np.hanning(2 * halfwidth) elif window == "hamming": if ww == 0: w = np.hamming(self.numfreq) else: pos = int((cf - self.lowF) / self.deltaF) halfwidth = int(ww / (2.0 * self.deltaF)) w = np.zeros(self.numfreq) w[pos - halfwidth:pos + halfwidth] = np.hamming(2 * halfwidth) elif window == "blackman": if ww == 0: w = np.blackman(self.numfreq) else: pos = int((cf - self.lowF) / self.deltaF) halfwidth = int(ww / (2.0 * self.deltaF)) w = np.zeros(self.numfreq) w[pos - halfwidth:pos + halfwidth] = np.blackman(2 * halfwidth) self.data = self.data * w self.done()
def test_calculate_lanczos_kernel(self): """ Tests the kernels implemented in C against their numpy counterpart. """ x = np.linspace(-5, 5, 11) values = calculate_lanczos_kernel(x, 5, "hanning") np.testing.assert_allclose( values["only_sinc"], np.sinc(x), atol=1E-9) np.testing.assert_allclose( values["only_taper"], np.hanning(len(x)), atol=1E-9) np.testing.assert_allclose( values["full_kernel"], np.sinc(x) * np.hanning(len(x)), atol=1E-9) values = calculate_lanczos_kernel(x, 5, "blackman") np.testing.assert_allclose( values["only_sinc"], np.sinc(x), atol=1E-9) np.testing.assert_allclose( values["only_taper"], np.blackman(len(x)), atol=1E-9) np.testing.assert_allclose( values["full_kernel"], np.sinc(x) * np.blackman(len(x)), atol=1E-9) values = calculate_lanczos_kernel(x, 5, "lanczos") np.testing.assert_allclose( values["only_sinc"], np.sinc(x), atol=1E-9) np.testing.assert_allclose( values["only_taper"], np.sinc(x / 5.0), atol=1E-9) np.testing.assert_allclose( values["full_kernel"], np.sinc(x) * np.sinc(x / 5.0), atol=1E-9)
def noiseFilter(data_in): N = int(np.ceil((4 / b))) if not N % 2: N += 1 # Make sure that N is odd. n = np.arange(N) # Compute a low-pass filter with cutoff frequency fH. hlpf = np.sinc(2 * fH * (n - (N - 1) / 2.)) hlpf *= np.blackman(N) hlpf = hlpf / np.sum(hlpf) # Compute a high-pass filter with cutoff frequency fL. hhpf = np.sinc(2 * fL * (n - (N - 1) / 2.)) hhpf *= np.blackman(N) hhpf = hhpf / np.sum(hhpf) hhpf = -hhpf hhpf[(N - 1) / 2] += 1 # Convolve both filters. h = np.convolve(hlpf, hhpf) s = np.convolve(data_in, hlpf) fig, ax = plt.subplots() ax.plot(data_in) plt.show() fig1, ax1 = plt.subplots() ax1.plot(s) plt.show() return s
def receiving(self, y): received = '' for x in range(0, len(y), len(generator.time_segment)): segment = y[x: x+len(generator.time_segment)] fft_segment = numpy.fft.fft(segment*numpy.blackman(len(segment))) fft_segment /= max(abs(fft_segment)) freqs = numpy.fft.fftfreq(fft_segment.size, d=1 / generator.sampling_frequency) peak_value_index = numpy.argmax(fft_segment[0:fft_segment.size / 4]) """ code alphabet: f1 = 00 f2 - 01 f3 - 10 f4 - 11 """ if freqs[peak_value_index] == generator.frequency: received += "00" elif freqs[peak_value_index] == generator.frequency2: received += "01" elif freqs[peak_value_index] == generator.frequency3: received += "10" elif freqs[peak_value_index] == generator.frequency4: received += "11" return received
def smooth(input_data, nth_octave = 6, window_type='hamming'): """ Smooth input data over 1/n octave """ f_min = 30 f_max = 20e3 number_of_octaves = math.log(f_max / f_min, 2) # ideally, this should be computed from the display resolution number_of_points = 4048 points_per_octave = number_of_points / number_of_octaves log_data = _distribute_over_log(input_data, f_min, f_max, number_of_points) window_length = points_per_octave / nth_octave if window_type == 'hamming': window = np.hamming(window_length) elif window_type == 'bartlett': window = np.bartlett(window_length) elif window_type == 'blackman': window = np.blackman(window_length) elif window_type == 'hanning': window = np.hanning(window_length) output = np.convolve(window / window.sum(), log_data, mode='same') return output
def _sweep_harmonics_responses(self, response, N, freqlist, shift=True): g = self.input_signal.ptp() / 2 di = self._fft_convolve(self.sweep_inverse_signal, response / g) # deconvolved impulse response imp_indices = numpy.zeros( N + 1, dtype=int ) # the indices of each impulse (1st linear, 2nd the first harm. dist. etc.) imp_indices[0] = len(self.sweep_inverse_signal) - 1 for n in range(1, N + 1): imp_indices[n] = imp_indices[0] - int(round(math.log(n + 1) * self.sweep_rate)) imps = [] for n in range(N): dl = (imp_indices[n] - imp_indices[n + 1]) // 2 lo = imp_indices[n] - dl # the low limit where to cut hi = imp_indices[n] + dl # the high limit where to cut di_w = di[lo:hi] win = numpy.blackman(len(di_w)) if len(di.shape) == 2: win = win.reshape((len(win), 1)) di_w *= win # smoothed version w = freqlist if shift: w = w * (n + 1) h = scipy.signal.freqz(di_w, worN=w)[1] off = imp_indices[n] - lo h *= numpy.exp(off * 1j * freqlist) imps.append(h) return imps
def freqCount(filename): noteFrequencyList = [] chunk = 8192 # open up a wave wf = wave.open(filename, 'rb') swidth = wf.getsampwidth() RATE = wf.getframerate() # use a Blackman window window = np.blackman(chunk) # read some data data = wf.readframes(chunk) # play stream and find the frequency of each chunk FrequencyList = [] while len(data) == chunk*swidth*wf.getnchannels(): # unpack the data and times by the hamming window indata = np.array(wave.struct.unpack("%dh"%(len(data)/swidth),data))*window # Take the fft and square each value fftData=abs(np.fft.rfft(indata))**2 # find the maximum which = fftData[1:].argmax() + 1 # use quadratic interpolation around the max if which != len(fftData)-1: y0,y1,y2 = np.log(fftData[which-1:which+2:]) x1 = (y2 - y0) * .5 / (2 * y1 - y2 - y0) # find the frequency and output it thefreq = (which + x1) * RATE / chunk FrequencyList.append(thefreq) else: thefreq = which*RATE/chunk FrequencyList.append(thefreq) # read some more data data = wf.readframes(chunk) for i in range(len(FrequencyList)): if((FrequencyList[1] < 16.835) or ((FrequencyList[i]>31.78) and (FrequencyList[i]<33.67)) or ((FrequencyList[i]>63.575) and (FrequencyList[i]<67.355))or((FrequencyList[i]>127.14) and (FrequencyList[i]<134.705)) or ((FrequencyList[i]>254.285) and (FrequencyList[i]<269.405)) or ((FrequencyList[i]>508.565) and (FrequencyList[i]<538.805)) or ((FrequencyList[i]>1017.135) and (FrequencyList[i]<1077.615)) or ((FrequencyList[i]>2034.27) and (FrequencyList[i]<2155.235)) or ((FrequencyList[i]>4068.54) and (FrequencyList[i]<4310.465)) or ((FrequencyList[i]>8137.076) and (FrequencyList[i]<8620.93)) or (FrequencyList[i]>16000)): noteFrequencyList.append('C') elif((FrequencyList[i]>16.835 and FrequencyList[i]<17.835) or (FrequencyList[i]>33.67 and FrequencyList[i]<35.675)or(FrequencyList[i]>67.355 and FrequencyList[i]<71.36) or (FrequencyList[i]>134.705 and FrequencyList[i]<142.715) or (FrequencyList[i]>269.405 and FrequencyList[i]<285.42) or (FrequencyList[i]>538.805 and FrequencyList[i]<570.845) or (FrequencyList[i]>1077.615 and FrequencyList[i]<1141.69) or (FrequencyList[i]>2155.235 and FrequencyList[i]<2283.39) or (FrequencyList[i]>4310.465 and FrequencyList[i]<4566.78) or (FrequencyList[i]>8620.93 and FrequencyList[i]<9133.555)): noteFrequencyList.append('C#') elif((FrequencyList[i]>17.835 and FrequencyList[i]<18.895) or (FrequencyList[i]>35.675 and FrequencyList[i]<37.805)or(FrequencyList[i]>71.36 and FrequencyList[i]<75.6) or (FrequencyList[i]>142.715 and FrequencyList[i]<151.195) or (FrequencyList[i]>285.42 and FrequencyList[i]<302.395) or (FrequencyList[i]>570.845 and FrequencyList[i]<604.79) or (FrequencyList[i]>1141.69 and FrequencyList[i]<1209.58) or (FrequencyList[i]>2283.39 and FrequencyList[i]<2419.17) or (FrequencyList[i]>4566.78 and FrequencyList[i]<4838.335) or (FrequencyList[i]>9133.555 and FrequencyList[i]<9676.665)): noteFrequencyList.append('D') elif((FrequencyList[i]>18.895 and FrequencyList[i]<20.02) or (FrequencyList[i]>37.805 and FrequencyList[i]<40.05)or(FrequencyList[i]>75.6 and FrequencyList[i]<80.095) or (FrequencyList[i]>151.195 and FrequencyList[i]<160.185) or (FrequencyList[i]>302.395 and FrequencyList[i]<320.375) or (FrequencyList[i]>604.79 and FrequencyList[i]<640.75) or (FrequencyList[i]>1209.58 and FrequencyList[i]<1281.51) or (FrequencyList[i]>2419.17 and FrequencyList[i]<2563.02) or (FrequencyList[i]>4838.335 and FrequencyList[i]<5126.035) or (FrequencyList[i]>9676.665 and FrequencyList[i]<10252.07)): noteFrequencyList.append('D#') elif((FrequencyList[i]>20.02 and FrequencyList[i]<21.215) or (FrequencyList[i]>40.05 and FrequencyList[i]<42.425)or(FrequencyList[i]>80.095 and FrequencyList[i]<84.86) or (FrequencyList[i]>160.185 and FrequencyList[i]<169.71) or (FrequencyList[i]>320.375 and FrequencyList[i]<339.42) or (FrequencyList[i]>640.75 and FrequencyList[i]<678.85) or (FrequencyList[i]>1281.51and FrequencyList[i]<1357.71) or (FrequencyList[i]>2563.02 and FrequencyList[i]<2715.425) or (FrequencyList[i]>5126.035 and FrequencyList[i]<5430.845) or (FrequencyList[i]>10252.07 and FrequencyList[i]<10861.69)): noteFrequencyList.append('E') elif((FrequencyList[i]>21.215 and FrequencyList[i]<22.475) or (FrequencyList[i]>42.425 and FrequencyList[i]<44.945)or(FrequencyList[i]>84.86 and FrequencyList[i]<89.905) or (FrequencyList[i]>169.71 and FrequencyList[i]<179.805) or (FrequencyList[i]>339.42 and FrequencyList[i]<359.605) or (FrequencyList[i]>678.85 and FrequencyList[i]<719.22) or (FrequencyList[i]>1357.71 and FrequencyList[i]<1438.445) or (FrequencyList[i]>2715.425 and FrequencyList[i]<2876.895) or (FrequencyList[i]>5430.845 and FrequencyList[i]<5753.78) or (FrequencyList[i]>10861.69 and FrequencyList[i]<11507.56)): noteFrequencyList.append('F') elif((FrequencyList[i]>22.475 and FrequencyList[i]<23.81) or (FrequencyList[i]>44.945 and FrequencyList[i]<47.62)or(FrequencyList[i]>89.905 and FrequencyList[i]<95.25) or (FrequencyList[i]>179.805 and FrequencyList[i]<190.5) or (FrequencyList[i]>359.605 and FrequencyList[i]<380.99) or (FrequencyList[i]>719.22 and FrequencyList[i]<761.99) or (FrequencyList[i]>1438.445 and FrequencyList[i]<1523.98) or (FrequencyList[i]>2876.895 and FrequencyList[i]<3047.96) or (FrequencyList[i]>5753.78 and FrequencyList[i]<6095.92) or (FrequencyList[i]>11507.56 and FrequencyList[i]<12191.8)): noteFrequencyList.append('F#') elif((FrequencyList[i]>23.81 and FrequencyList[i]<25.23) or (FrequencyList[i]>47.62 and FrequencyList[i]<50.455)or(FrequencyList[i]>95.25 and FrequencyList[i]<100.915) or (FrequencyList[i]>190.5 and FrequencyList[i]<201.825) or (FrequencyList[i]>380.99 and FrequencyList[i]<403.65) or (FrequencyList[i]>761.99 and FrequencyList[i]<807.3) or (FrequencyList[i]>1523.98 and FrequencyList[i]<1614.6) or (FrequencyList[i]>3047.96 and FrequencyList[i]<3229.2) or (FrequencyList[i]>6095.92 and FrequencyList[i]<6458.405) or (FrequencyList[i]>12191.8 and FrequencyList[i]<12916.8)): noteFrequencyList.append('G') elif((FrequencyList[i]>25.23 and FrequencyList[i]<26.73) or (FrequencyList[i]>50.455 and FrequencyList[i]<53.455)or(FrequencyList[i]>100.915 and FrequencyList[i]<106.915) or (FrequencyList[i]>201.825 and FrequencyList[i]<213.825) or (FrequencyList[i]>403.65 and FrequencyList[i]<427.655) or (FrequencyList[i]>807.3 and FrequencyList[i]<855.305) or (FrequencyList[i]>1614.6 and FrequencyList[i]<1710.61) or (FrequencyList[i]>3229.2 and FrequencyList[i]<3421.22) or (FrequencyList[i]>6458.405 and FrequencyList[i]<6824.44) or (FrequencyList[i]>12916.8 and FrequencyList[i]<13684.88)): noteFrequencyList.append('G#') elif((FrequencyList[i]>26.73 and FrequencyList[i]<28.3175) or (FrequencyList[i]>53.455 and FrequencyList[i]<56.635)or(FrequencyList[i]>106.915 and FrequencyList[i]<113.27) or (FrequencyList[i]>213.825 and FrequencyList[i]<226.54) or (FrequencyList[i]>427.655 and FrequencyList[i]<453.082) or (FrequencyList[i]>855.305 and FrequencyList[i]<906.165) or (FrequencyList[i]>1710.61 and FrequencyList[i]<1812.33) or (FrequencyList[i]>3421.22 and FrequencyList[i]<3624.555) or (FrequencyList[i]>6824.44 and FrequencyList[i]<7249.31) or (FrequencyList[i]>13684.88 and FrequencyList[i]<13684.88)): noteFrequencyList.append('A') elif((FrequencyList[i]>28.3175 and FrequencyList[i]<29.9975) or (FrequencyList[i]>56.635 and FrequencyList[i]<60.005)or(FrequencyList[i]>113.27 and FrequencyList[i]<120.005) or (FrequencyList[i]>226.54 and FrequencyList[i]<240.01) or (FrequencyList[i]>453.082 and FrequencyList[i]<480.022) or (FrequencyList[i]>906.165 and FrequencyList[i]<960.05) or (FrequencyList[i]>1812.33 and FrequencyList[i]<1920.095) or (FrequencyList[i]>3624.555 and FrequencyList[i]<3840.19) or (FrequencyList[i]>7249.31 and FrequencyList[i]<7680.376) or (FrequencyList[i]>13684.88 and FrequencyList[i]<14498.5)): noteFrequencyList.append('A#') else: noteFrequencyList.append('B') return noteFrequencyList
def main(): if len(sys.argv) > 1: wf = wave.open(sys.argv[1],'rb') firstTone = False else: inp = raw_input('Press enter to start record') while inp: inp = raw_input('Press enter to start record') rec = Recorder(channels = 1) with rec.open('Test.wav','wb') as recfile: recfile.start_recording() print 'Start recording...' inp = raw_input('Press enter to stop') while inp: inp = raw_input('Press enter to stop') recfile.stop_recording() wf = wave.open('Test.wav', 'rb') firstTone = True ScaleList = getScale(0, Tones) curPos = 0 swidth = wf.getsampwidth() RATE = wf.getframerate() window = np.blackman(chunk) p = pyaudio.PyAudio() stream = p.open(format = p.get_format_from_width(wf.getsampwidth()), channels = wf.getnchannels(), rate = RATE, output = True) data = wf.readframes(chunk) values = [] while len(data) == chunk*swidth: stream.write(data) if ( firstTone == False): thefreq = getHz( swidth, window, RATE, data ) posTone = binaryNoteSearch(thefreq, Tones) if posTone != -1: ScaleList = getScale( posTone, Tones ) firstTone = True curPos = 0 print "The freq is %f Hz. Note: %s" % ( round(thefreq), Tones[posTone].NoteName ) else: thefreq = getHz( swidth, window, RATE, data ) if( thefreq > ScaleList[curPos].HighFreq or ScaleList[curPos].LowFreq > thefreq ): posTone = binaryNoteSearch(thefreq, ScaleList) if posTone != -1: if posTone != 16: values.append(posTone) if len(values) == 2: Text = getString(values) sys.stdout.write(Text) values = [] sys.stdout.flush() curPos = posTone; data = wf.readframes(chunk) Text = getString(values) print Text p.terminate()
def get_wave_data(self, file_path): with wave.open(file_path, 'rb') as wf: sample_width = wf.getsampwidth() frame_rate = wf.getframerate() num_frames = wf.getnframes() length_in_seconds = num_frames / (frame_rate * 1.0) num_iterations = int(length_in_seconds * 2) iteration_size = int(num_frames / num_iterations) wave_data = [] for fragment_num in range(0, num_iterations): data = wf.readframes(iteration_size) window_size = len(data) / sample_width window = np.blackman(window_size) fragment_data = wave.struct.unpack("%dh" % window_size, data) * window fft_data = abs(np.fft.rfft(fragment_data)) ** 2 wave_data = np.hstack((wave_data, fft_data[:100])) # take only 100 frequences return wave_data
def __init__(self, sample_rate, fft_peak=7.0, sample_format=None, search_size=1, verbose=False, signal_width=40e3): self._sample_rate = sample_rate self._fft_size=int(math.pow(2, 1+int(math.log(self._sample_rate/1000,2)))) # fft is approx 1ms long self._bin_size = float(self._fft_size)/self._sample_rate * 1000 # How many ms is one fft now? self._verbose = verbose self._search_size = search_size self._fft_peak = fft_peak if sample_format == "rtl": self._struct_elem = numpy.uint8 self._struct_len = numpy.dtype(self._struct_elem).itemsize * self._fft_size *2 elif sample_format == "hackrf": self._struct_elem = numpy.int8 self._struct_len = numpy.dtype(self._struct_elem).itemsize * self._fft_size *2 elif sample_format == "float": self._struct_elem = numpy.complex64 self._struct_len = numpy.dtype(self._struct_elem).itemsize * self._fft_size else: raise Exception("No sample format given") self._window = numpy.blackman(self._fft_size) self._fft_histlen=500 # How many items to keep for moving average. 5 times our signal length self._data_histlen=self._search_size self._data_postlen=5 self._signal_maxlen=1+int(30/self._bin_size) # ~ 30 ms self._fft_freq = numpy.fft.fftfreq(self._fft_size) self._signal_width=signal_width/(self._sample_rate/self._fft_size) # Area to ignore around an already found signal in Hz if self._verbose: print "fft_size=%d (=> %f ms)"%(self._fft_size,self._bin_size) print "calculate fft once every %d block(s)"%(self._search_size) print "require %.1f dB"%(10*math.log(self._fft_peak,10)) print "signal_width: %d (= %.1f Hz)"%(self._signal_width,self._signal_width*self._sample_rate/self._fft_size)
def plotWindowFunc(): plt.clf() plt.plot(np.arange(20), np.kaiser(20,3.5)) plt.plot(np.arange(20), np.bartlett(20)) plt.plot(np.arange(20), np.blackman(20)) plt.plot(np.arange(20), np.hamming(20)) plt.plot(np.arange(20), np.hanning(20))
def Execute(self,data): #compute power in both components pReal = (data['real']/2.0**self.bits) pImag = (data['imag']/2.0**self.bits) # create empty complex array to combine pReal and pImag data = np.empty(pReal.shape, dtype=complex) data.real = pReal; data.imag = pImag; # subtract average dc from each range dc = np.mean(data,axis=0) data = np.subtract(data[:,],dc) data = np.clip(data,1e-15,np.max(data)) coeff = np.blackman(64) for i in range(0,data.shape[1]): data[:,i] = np.convolve(data[:,i],coeff,'same') # compute complex 256-point for each range cell dMap = np.fft.fft(data,256, axis=0) dMap = np.fft.fftshift(dMap,axes=(0,)) # convert values to dB dMap = 20*np.log10(np.abs(dMap)); return dMap
def _update_mode(self): if self.allocation.width <= 0: return if self.fft_show: max_freq = (self.freq_div * self.get_ticks()) wanted_step = 1.0 / max_freq / 2 * self._input_freq self.input_step = max(floor(wanted_step), 1) self.draw_interval = 5.0 self.set_max_samples( ceil(self.allocation.width / \ float(self.draw_interval) * 2) * self.input_step) # Create the (blackman) window self.fft_window = blackman( ceil(self.allocation.width / float(self.draw_interval) * 2)) self.draw_interval *= wanted_step / self.input_step else: # Factor is just for triggering: time = (self.time_div * self.get_ticks()) if time == 0: return samples = time * self._input_freq self.set_max_samples(samples * self.max_samples_fact) self.input_step = max(ceil(samples\ / (self.allocation.width / 3.0)), 1) self.draw_interval = self.allocation.width\ / (float(samples) / self.input_step) self.fft_window = None
def doPitchDetect(self): self.frames = [] # play stream and find the frequency of each chunk swidth = 2 window = np.blackman(self.CHUNK) data = self.micStream.read(self.CHUNK) self.frames.append(data) # unpack the data and times by the hamming window indata = np.array(wave.struct.unpack("%dh"%(len(data)/swidth), data))*window # Take the fft and square each value fftData=abs(np.fft.rfft(indata))**2 # find the maximum which = fftData[1:].argmax() + 1 # use quadratic interpolation around the max if which != len(fftData)-1: y0,y1,y2 = np.log(fftData[which-1:which+2:]) x1 = (y2 - y0) * .5 / (2 * y1 - y2 - y0) # find the frequency theFreq = (which+x1)*self.RATE/self.CHUNK/2 if (theFreq > 300 and theFreq < 715): self.checkFreq(theFreq) else: theFreq = which*self.RATE/self.CHUNK/2 if (theFreq > 300 and theFreq < 715): self.checkFreq(theFreq)
def single_taper_spectrum(data, delta, taper_name=None): """ Returns the spectrum and the corresponding frequencies for data with the given taper. """ length = len(data) good_length = length // 2 + 1 # Create the frequencies. # XXX: This might be some kind of hack freq = abs(np.fft.fftfreq(length, delta)[:good_length]) # Create the tapers. if taper_name == 'bartlett': taper = np.bartlett(length) elif taper_name == 'blackman': taper = np.blackman(length) elif taper_name == 'boxcar': taper = np.ones(length) elif taper_name == 'hamming': taper = np.hamming(length) elif taper_name == 'hanning': taper = np.hanning(length) elif 'kaiser' in taper_name: taper = np.kaiser(length, beta=14) # Should never happen. else: msg = 'Something went wrong.' raise Exception(msg) # Detrend the data. data = detrend(data) # Apply the taper. data *= taper spec = abs(np.fft.rfft(data)) ** 2 return spec, freq
def blackman_window(self, show=0): apod = N.blackman(self.data_points) for i in range(2): self.the_result.y[i] = self.the_result.y[i]*apod if show == 1: return self.the_result return self
def smavg(): # 权重设置 weights_exp=np.exp(np.linspace(-1,0,N)) weights_exp/=weights_exp.sum() weights_sim=np.ones(N) weights_sim/=weights_sim.sum() weights_blw=np.blackman(N) weights_blw/=weights_blw.sum() # 平滑操作 sm_exp=np.convolve(weights_exp,data)[N-1:-N+1] sm_sim=np.convolve(weights_sim ,data)[N-1:-N+1] sm_blw=np.convolve(weights_blw ,data)[N-1:-N+1] #np.savetxt('result',expa) exp_mean=1.01*np.average(sm_exp) sim_mean=1.02*np.average(sm_sim) #sub mean #expa=expa-exp_mean #sima=sima-sim_mean # 绘图 #plt.plot(t,data[N-1:],lw=1.0) #plt.figure() plt.plot(t,data[N-1:],'k',label='origin') #plt.plot(t,sm_exp,'r',label='exp avg') #指数移动平均 #plt.plot(t,sm_sim,'g',label='sim avg') #简单移动平均 plt.plot(t,sm_blw,'y',lw=2.0,label='blackman win avg') #布莱克曼窗函数 plt.legend(loc='upper center') #plt.axhline(y=exp_mean,lw=2,color='y') #plt.axhline(y=sim_mean,lw=2,color='b') plt.show()
def apply_filter(self, array): if len(array.shape)!=1: return False # need 2D data nx = array.shape[0] # Apodization function if self.type == 1: ft = np.bartlett(nx) elif self.type == 2: ft = np.blackman(nx) elif self.type == 3: ft = np.hamming(nx) elif self.type == 4: ft = np.hanning(nx) elif self.type == 5: # Blackman-Harris window a0 = 0.35875 a1 = 0.48829 a2 = 0.14128 a3 = 0.01168 x = np.linspace(0,1,nx) ft = a0 - a1*np.cos(2*np.pi*x) + a2*np.cos(4*np.pi*x) + a3*np.cos(6*np.pi*x) elif self.type == 6: # Lanczos window x = np.linspace(-1,1,nx) ft = np.sinc(x) elif self.type == 7: x = np.linspace(-1,1,nx) exec('x='+self.custom) ft = x else: ft = np.ones(nx) array.data = array.data*ft return True
def filter(self, samplingRate, cutoffFrequency, filterLength): """This function creates a base filter, in this case a low pass filter. :param samplingRate: Rate at which the signal should be sampled in Hz :param cutoffFrequency: Frequency at which we should begin filtering :param filterLength: Length of the filter. :returns: A sinc filter """ # Configuration. fS = samplingRate # Sampling rate. fL = cutoffFrequency # Cutoff frequency. N = filterLength # Filter length, must be odd. # Compute sinc filter. h = np.sinc(2 * fL / fS * (np.arange(N) - (N - 1) / 2.)) # Apply window. h *= np.blackman(N) # Normalize to get unity gain. h /= np.sum(h) return h
def hpf(): """ Ref: https://tomroelandts.com/articles/how-to-create-a-simple-high-pass-filter Usage: h = hpf() s = np.convolve(s, h) """ fc = 200.0 / 16000 b = 150.0 / 16000 N = int(np.ceil((4 / b))) if not N % 2: N += 1 # N, odd n = np.arange(N) # compute a low-pass filter h = np.sinc(2 * fc * (n - (N - 1) / 2.)) w = np.blackman(N) h = h * w h = h / np.sum(h) # spectral inversion, make high-pass filter h = -h h[(N - 1) / 2] += 1 return h
def get_freq2(sample, rate): sample_len = 22100 frequencies = (np.arange(0, sample_len/2+1)).astype('float')*rate/sample_len avg_sample = np.convolve(sample, np.ones((5,))) avg_sample = avg_sample[2:-2] window = np.blackman(len(sample)) fft_data4 = np.log(abs(np.fft.rfft(avg_sample*window, sample_len))**2) w = 50 t = 3 peaks = [] for j in range(0,len(fft_data4)-w): mx_i = np.argmax(fft_data4[j:j+w]) strength = fft_data4[j+mx_i]-np.median(fft_data4[j:j+w]) if mx_i == w/2 and strength > t: d_x = frequencies[j+mx_i] y0,y1,y2 = fft_data4[j+mx_i-1:j+mx_i+2] x1 = (y2 - y0) * .5 / (2 * y1 - y2 - y0) peaks.append([d_x, x1, strength]) peaks = np.array(peaks) (freq, new_peaks) = freq_from_harmonics(peaks) return get_note(freq)
def plot_spectrogram(x, fs, filename,nfft): cf=0.0 plt.figure(figsize=(18,20)) fig, ax1 = plt.subplots(nrows=1) from matplotlib import pylab #wrapper = lambda n: np.kaiser(n,40) wrapper = lambda n : np.blackman(n) #wrapper = lambda n : np.hamming(n) #wrapper = lambda n : np.hanning(n) #Pxx, freqs, time, im = ax1.specgram(x, NFFT=nfft, Fs=fs, detrend=pylab.detrend_none, noverlap=nfft/2, window=wrapper(nfft)) Pxx, freqs, time, im = ax1.specgram(x, Fs=fs, NFFT=nfft) ax1.set_title('specgram spectgm'+'NFFT= %d'%nfft) #ax3.axis('tight') #labels = [item.get_text() for item in ax1.get_xticklabels()] ax1.set_ylabel('frequency(Hz)') ax1.set_xlabel('time') #ax1.set_ylim(40000,80000.0) fig.colorbar(im, ax=ax1).set_label("Amplitude (dB)") #ax1.set_xlim(0,7) #c=ax1.get_yticks().tolist() #print c #a=[str(float((i+cf)/1000.0)) for i in c ] #print a #ax1.set_yticklabels(a) #ax1.set_ylim(30,40) plt.savefig(filename+'.pdf')
def play_(self): wf = wave.open('output.wav', 'rb') chunk = 2048 swidth = wf.getsampwidth() RATE = wf.getframerate() window = np.blackman(chunk) p = pyaudio.PyAudio() stream = p.open(format=p.get_format_from_width(wf.getsampwidth()), channels=wf.getnchannels(), rate=RATE, output=True) data = wf.readframes(chunk) thefreq = [] while len(data) == chunk * swidth: stream.write(data) indata = np.array(wave.struct.unpack("%dh" % (len(data) / swidth), data)) * window fftData = abs(np.fft.rfft(indata)) ** 2 which = fftData[1:].argmax() + 1 if which != len(fftData) - 1: y0, y1, y2 = np.log(fftData[which - 1:which + 2:]) x1 = (y2 - y0) * .5 / (2 * y1 - y2 - y0) thefreq.append((which + x1) * RATE / chunk) else: thefreq.append(which * RATE / chunk) data = wf.readframes(chunk) if data: stream.write(data) stream.close() p.terminate() self.olahFrequency(thefreq)
def smooth(x, windowLen, windowType="boxcar"): """Smooth a numpy array, returning the smoothed values Adapted from http://www.scipy.org/Cookbook/SignalSmooth""" if x.ndim != 1: raise ValueError("smooth only accepts 1 dimension arrays.") if x.size < windowLen: raise ValueError("Input vector needs to be bigger than window size.") if windowLen < 3: return x if windowType == "boxcar": w = np.ones(windowLen,'d') elif windowType == "hamming": w = np.hamming(windowLen) elif windowType == "hanning": w = np.hanning(windowLen) elif windowType == "bartlett": w = np.bartlett(windowLen) elif windowType == "blackman": w = np.blackman(windowLen) else: raise ValueError("windowType %s is not one of 'boxcar', 'hanning', 'hamming', 'bartlett', 'blackman'" % windowType) s = np.r_[x[windowLen-1:0:-1],x,x[-1:-windowLen:-1]] y = np.convolve(w/w.sum(), s, mode='valid') return y[windowLen//2:-windowLen//2 + 1]
def get_iprobe(self, leakage=None, t_comp=None): """ main purpose is to subtract leakage currents Will use the full data, as the t_range is meant to be plasma interval returns a copy of the measured courremt, overwritten with the corrected iprobe """ # obtain leakage estimate if t_comp is None: t_comp = self.t_comp FFT_size = nice_FFT_size(len(self.imeasfull.timebase), -1) self.iprobefull = self.imeasfull.copy() self.sweepQ = [] # will keep these for synchronous sampling input_leakage = leakage for (c, chan) in enumerate(self.imeasfull.channels): if self.select is not None and c not in self.select: continue leakage = input_leakage cname = chan.config_name sweepV = self.vcorrfull.signal[self.vlookup[self.vassoc[c]]][0:FFT_size] sweepQ = hilbert(sweepV) self.sweepQ.append(sweepQ) # save for synchronising segments (it is smoothed) # these attempts to make it accept a single channel are only partial imeas = self.imeasfull.signal[c] # len(self.imeasfull.channels) >1 else self.imeasfull.signal tb = self.imeasfull.timebase w_comp = np.where((tb>=t_comp[0]) & (tb<=t_comp[1]))[0] if len(w_comp) < 2000: raise ValueError('Not enough points {wc} t_comp - try {tt}' .format(tt=np.round([tb[0], tb[0] + t_comp[1]-t_comp[0]],3), wc=len(w_comp))) ns = len(w_comp) wind = np.blackman(ns) offset = np.mean(wind * imeas[w_comp])/np.mean(wind) sweepVFT = np.fft.fft(AC(sweepV[w_comp]) * wind) imeasFT = np.fft.fft(AC(imeas[w_comp]) * wind) ipk = np.argmax(np.abs(sweepVFT)[0:ns//2]) # avoid the upper one comp = imeasFT[ipk]/sweepVFT[ipk] #print('leakage compensation factor = {r:.2e} + j{i:.2e}' # .format(r=np.real(comp), i=np.imag(comp))) print('{u}sing computed leakage comp factor = {m:.2e} e^{p:.2f}j' .format(u = ["Not u", "U"][leakage is None], m=np.abs(comp), p=np.angle(comp))) if leakage is None: leakage = [np.real(comp), np.imag(comp)] # find the common length - assuming they start at the same time???? comlen = min(len(self.imeasfull.timebase),len(self.vmeasfull.timebase),len(sweepQ)) # put signals back into rdata (original was copied by reduce_time) # overwrite - is this OK? self.iprobefull.signal[c] = self.iprobefull.signal[c]*0. # clear it # sweepV has a DC component! beware self.iprobefull.signal[c][0:comlen] = self.imeasfull.signal[c][0:comlen]-offset \ - sweepV[0:comlen] * leakage[0] - sweepQ[0:comlen] * leakage[1] # remove DC cpt (including that from the compensation sweepV) offset = np.mean(wind * self.iprobefull.signal[c][w_comp])/np.mean(wind) self.iprobefull.signal[c][0:comlen] -= offset
def __init__(self): self.samplerate = 2e5 self.frequency = 200 self.length = self.frequency*10 self.fftsample = 512 #self.timeshift = 128 self.blackman = numpy.blackman(self.fftsample) self.signal = [math.sin(2*math.pi*self.frequency*i/self.samplerate) for i in xrange(self.length)]
def SelectWindowsFun(self, index): #global window x = {0: np.ones(self.CHUNK), 1: np.hamming(self.CHUNK), 2: np.hanning(self.CHUNK), 3: np.bartlett(self.CHUNK), 4: np.blackman(self.CHUNK)} self.window = x[index]
def callback(in_data, frame_count, time_info, status): window = np.blackman(frame_count) # unpack the data and times by the hamming window indata = np.array(wave.struct.unpack('{n}h'.format(n=frame_count), in_data))*window freq = getMainFreq(indata, frame_count) note = bt.getNote(freq) print note return (in_data, pyaudio.paContinue)
def Smooth(ToSmooth,GaussianWidth=0.05): BlurWidth = int(GaussianWidth*len(ToSmooth)) print BlurWidth if(BlurWidth*numpy.size(ToSmooth)/2 < 1.4 or BlurWidth == 2): return ToSmooth else: Cnv = numpy.blackman(BlurWidth)/(numpy.hanning(BlurWidth).sum()) return numpy.convolve(ToSmooth,Cnv,mode='same')
def define_filt(fc, b, window, type_filt): """Define a lp or a hp filter Args: fc (float): cutoff frequency, as a fraction of sampling rate b (float): transition band, as a fraction of sampling rate window (str): window sinc filter, options 'none', 'blackman', 'hanning' type_filt (str): low pass or high pass filter, options 'lp', 'hp' Returns: n (int array): span of filter sinc (float array): sinc filter in time domain """ # NOTE: do some arg checks here if you want a more robust function # more on this below, but now need to make sure that ceil(4/b) is odd N = int(np.ceil((4 / b))) # make sure filter length is odd if not N % 2: N += 1 # generate span over which to eval sinc function n = np.arange(N) # Compute the filter sinc_func = np.sinc(2 * fc * (n - (N - 1) / 2.)) # generate our window if window == 'blackman': win = np.blackman(N) elif window == 'hanning': win = np.hanning(N) elif window == 'none': # if 'none' then just an array of ones so that the values in the sinc aren't modified win = np.ones(N) else: print('Unknown window type') # apply the windowing function sinc_func = sinc_func * win # Normalize to have an area of 1 (unit area) sinc_func /= np.sum(sinc_func) # check filter type...if lp then do nothing, else if hp invert, else return msg if type_filt == 'lp': return n, sinc_func elif type_filt == 'hp': # invert sinc_func = -1 * sinc_func # add 1 to middle of the inverted function sinc_func[int((N - 1) / 2)] += 1 return n, sinc_func else: print('error - specify lp or hp filter')
x = np.linspace(0, CHUNK / RATE, CHUNK) y = f(x) freqs = np.fft.fftfreq(y.size, x[1] - x[0]) app = QtGui.QApplication([]) w = QtGui.QMainWindow() cw = pg.GraphicsLayoutWidget() w.show() w.resize(1200, 800) w.setCentralWidget(cw) w.setWindowTitle('Fourier') p = cw.addPlot(row=0, col=0) p2 = cw.addPlot(row=1, col=0) p2.setLogMode(y=True) fi = 0 lim = 22 while True: fi += 0.00001 y = f(x + fi) FFT = (np.abs(np.fft.fft(y)) * np.blackman(CHUNK)).clip(min=1) FFT = np.where(FFT > 11, FFT, 1) p.plot(x, y, clear=True) p2.plot(freqs, FFT, clear=True) pg.QtGui.QApplication.processEvents() time.sleep(0.01)
h1 *= signal.tukey(Nt,alpha=0.05) dl = 1./4096 low_f = 30. high_f = 500. freqs = np.fft.rfftfreq(2*Nt, dl) freqs = freqs[:Nt/2+1] hf = np.fft.rfft(h1, n=2*Nt, norm = 'ortho') hf = hf[:Nt/2+1] print hf Pxx, frexx = mlab.psd(h1, Fs=4096, NFFT=2*4096,noverlap=4096/2,window=np.blackman(2*4096),scale_by_freq=False) hf_psd = interp1d(frexx,Pxx) hf_psd_data = abs(hf.copy()*np.conj(hf.copy())) mask = (freqs>low_f) & (freqs < high_f) mask2 = (freqs>80.) & (freqs < 300.) #plt.figure() #plt.loglog(hf_psd_data[mask]) #plt.loglog(hf_psd(freqs)[mask]) #plt.savefig('compare.pdf') norm = np.mean(hf_psd_data[mask])/np.mean(hf_psd(freqs)[mask]) norm2 = np.mean(hf_psd_data[mask2])/np.mean(hf_psd(freqs)[mask2])
def find_freq(filename, target, tolerance): #chunk = 1584 chunk = 1584 count = 0 countsound = 0 countpause = 0 issound = False ispause = False code = '' # open up a wave wf = wave.open(filename, 'rb') swidth = wf.getsampwidth() RATE = wf.getframerate() # use a Blackman window window = np.blackman(chunk) data = wf.readframes(chunk) #data = get_data(filename) # read some data5 if wf.getnchannels() == 2: data = audioop.tomono(data, swidth, .5, .5) # play stream and find the frequency of each chunk while len(data) == chunk * swidth: # unpack the data and times by the hamming window indata = np.array(wave.struct.unpack("%dh"%(len(data)/(swidth)),\ data))*window if (all(v == 0 for v in indata)): print "breaking on zero indata array" break # Take the fft and square each value fftData = abs(np.fft.rfft(indata))**2 # find the maximum which = fftData[1:].argmax() + 1 # use quadratic interpolation around the max if which != len(fftData) - 1: # freezing here y0, y1, y2 = np.log(fftData[which - 1:which + 2:]) x1 = (y2 - y0) * .5 / (2 * y1 - y2 - y0) # find the frequency and output it thefreq = (which + x1) * RATE / chunk print count, "The freq is %f Hz." % (thefreq) if thefreq > target - tolerance and thefreq < target + tolerance * 2: countsound += 1 issound = True if ispause == True: code += (str(countpause)) + ',' countpause = 0 ispause = False else: countpause += 1 ispause = True if issound == True: code += (str(countsound)) + ',' countsound = 0 issound = False else: thefreq = which * RATE / chunk print count, "The freq is %f Hz." % (thefreq) if thefreq > target - tolerance and thefreq < target + tolerance * 2: countsound += 1 issound = True if ispause == True: code += (str(countpause)) + ',' countpause = 0 ispause = False else: countpause += 1 ispause = True if issound == True: code += (str(countsound)) + ',' countsound = 0 issound = False count += 1 # read some more data data = wf.readframes(chunk) # read some data5 if wf.getnchannels() == 2: data = audioop.tomono(data, swidth, .5, .5) if len(code) % 2 == 0: code += str(countsound) + ',' else: code += str(countpause) + ',' print "returning %s.", code return code
def local_blackman(vec): return (blackman(len(vec)))
def apres_range(self, p, max_range=2000, winfun='blackman'): """ Parameters --------- self: class data object p: int pad factor, level of interpolation for fft winfun: str window function for fft Output -------- Rcoarse: array range to bin centres (m) Rfine: array range to reflector from bin centre (m) spec_cor: array spectrum corrected. positive frequency half of spectrum with ref phase subtracted. This is the complex signal which can be used for cross-correlating two shot segements. ### Original Matlab File Notes ### Phase sensitive processing of FMCW radar data based on Brennan et al. 2013 Based on Paul's scripts but following the nomenclature of: "Phase-sensitive FMCW radar imaging system for high precision Antarctic ice shelf profile monitoring" Brennan, Lok, Nicholls and Corr, 2013 Summary: converts raw FMCW radar voltages into a range for Craig Stewart 2013 April 24 Modified frequencies 10 April 2014 """ if self.flags.range != 0: raise TypeError( 'The range filter has already been done on these data.') # Processing settings nf = int(np.floor(p * self.snum / 2)) # number of frequencies to recover # TODO: implement all the other window functions if winfun not in ['blackman', 'bartlett', 'hamming', 'hanning', 'kaiser']: raise TypeError( 'Window must be in: blackman, bartlett, hamming, hanning, kaiser') elif winfun == 'blackman': win = np.blackman(self.snum) # Get the coarse range self.Rcoarse = np.arange(nf) * self.header.ci / (2 * self.header.bandwidth * p) # Calculate phase of each range bin centre for correction # eq 17: phase for each range bin centre (measured at t=T/2), given that tau = n/(B*p) self.phiref = 2.*np.pi*self.header.fc*np.arange(nf)/(self.header.bandwidth*p) - \ (self.header.chirp_grad*np.arange(nf)**2)/(2*self.header.bandwidth**2*p**2) # Measure the sampled IF signal: FFT to measure frequency and phase of IF #deltaf = 1/(T*p); # frequency step of FFT #f = [0:deltaf:fs/2-deltaf]; # frequencies measured by the fft - changed 16 April 2014, was #f = [0:deltaf:fs/2]; #Rcoarse = f*ci*T/(2*B); # Range at the centre of each range bin: eq 14 (rearranged) (p is accounted for inf) #Rcoarse = [0:1/p:T*fs/2-1/p]*ci/(2*B); # Range at the centre of each range bin: eq 14 (rearranged) (p is accounted for inf) # --- Loop through for each chirp in burst --- # # preallocate spec = np.zeros((nf, self.cnum)).astype(np.cdouble) spec_cor = np.zeros((nf, self.cnum)).astype(np.cdouble) for ii in range(self.cnum): # isolate the chirp and preprocess before transform chirp = self.data[:, ii].copy() chirp = chirp - np.mean(chirp) # de-mean chirp *= win # windowed # fourier transform fft_chirp = (np.sqrt(2. * p) / len(chirp)) * np.fft.fft( chirp, p * self.snum) # fft and scale for padding fft_chirp /= np.sqrt(np.mean(win**2.)) # scale with rms of window # output spec[:, ii] = fft_chirp[: nf] # positive frequency half of spectrum up to (nyquist minus deltaf) comp = np.exp( -1j * (self.phiref)) # unit phasor with conjugate of phiref phase spec_cor[:, ii] = comp * fft_chirp[: nf] # positive frequency half of spectrum with ref phase subtracted self.data = spec_cor.copy() self.Rfine = phase2range( np.angle(self.data), self.header.lambdac, np.transpose(np.tile(self.Rcoarse, (self.cnum, 1))), self.header.chirp_grad, self.header.ci) # Crop output variables to useful depth range only n = np.argmin(self.Rcoarse <= max_range) self.Rcoarse = self.Rcoarse[:n] self.Rfine = self.Rfine[:n, :] self.data = self.data[:n, :] self.snum = n self.flags.range = max_range
def demo4_procedural(): stratWindow = 0.5 * (np.blackman(256) + np.hanning(256)) stratWindow = stratWindow.reshape(1, stratWindow.size) basepath = Path(__file__).parent.parent.absolute() parStrat = { 'wavFile': basepath / 'Sounds/AzBio_3sent_65dBSPL.wav', # this should be a complete absolute path to your sound file of choice 'fs': 17400, # this value matches implant internal audio rate. incoming wav files resampled to match 'nFft': 256, 'nHop': 20, 'nChan': 15, # do not change 'startBin': 6, 'nBinLims': np.array([2, 2, 1, 2, 2, 2, 3, 4, 4, 5, 6, 7, 8, 10, 56]), 'window': stratWindow, 'pulseWidth': 18, # DO NOT CHANGE 'verbose': 0 } parReadWav = { 'parent': parStrat, 'tStartEnd': [], 'iChannel': 1, } parPre = { 'parent': parStrat, 'coeffNum': np.array([.7688, -1.5376, .7688]), 'coeffDenom': np.array([1, -1.5299, .5453]), } envCoefs = np.array([ -19, 55, 153, 277, 426, 596, 784, 983, 1189, 1393, 1587, 1763, 1915, 2035, 2118, 2160, 2160, 2118, 2035, 1915, 1763, 1587, 1393, 1189, 983, 784, 596, 426, 277, 153, 55, -19 ]) / (2**16) parAgc = { 'parent': parStrat, 'kneePt': 4.476, 'compRatio': 12, 'tauRelFast': -8 / (17400 * np.log(.9901)) * 1000, 'tauAttFast': -8 / (17400 * np.log(.25)) * 1000, 'tauRelSlow': -8 / (17400 * np.log(.9988)) * 1000, 'tauAttSlow': -8 / (17400 * np.log(.9967)) * 1000, 'maxHold': 1305, 'g0': 6.908, 'fastThreshRel': 8, 'cSlowInit': 0.5e-3, 'cFastInit': 0.5e-3, 'controlMode': 'naida', 'clipMode': 'limit', 'decFact': 8, 'envBufLen': 32, 'gainBufLen': 16, 'envCoefs': envCoefs } parWinBuf = {'parent': parStrat, 'bufOpt': []} parFft = { 'parent': parStrat, 'combineDcNy': False, 'compensateFftLength': False, 'includeNyquistBin': False } parHilbert = { 'parent': parStrat, 'outputOffset': 0, 'outputLowerBound': 0, 'outputUpperBound': np.inf } parEnergy = {'parent': parStrat, 'gainDomain': 'linear'} parNoiseReduction = { 'parent': parStrat, 'gainDomain': 'log2', 'tau_speech': .0258, 'tau_noise': .219, 'threshHold': 3, 'durHold': 1.6, 'maxAtt': -12, 'snrFloor': -2, 'snrCeil': 45, 'snrSlope': 6.5, 'slopeFact': 0.2, 'noiseEstDecimation': 1, 'enableContinuous': False, 'initState': { 'V_s': -30 * np.ones((15, 1)), 'V_n': -30 * np.ones((15, 1)) }, } parPeak = { 'parent': parStrat, 'binToLocMap': np.concatenate(( np.zeros(6, ), np.array([ 256, 640, 896, 1280, 1664, 1920, 2176, # 1 x nBin vector of nominal cochlear locations for the center frequencies of each STFT bin 2432, 2688, 2944, 3157, 3328, 3499, 3648, 3776, 3904, 4032, # values from 0 .. 15 in Q9 format 4160, 4288, 4416, 4544, 4659, 4762, 4864, 4966, 5069, 5163, # corresponding to the nominal steering location for each 5248, 5333, 5419, 5504, 5589, 5669, 5742, 5815, 5888, 5961, # FFT bin 6034, 6107, 6176, 6240, 6304, 6368, 6432, 6496, 6560, 6624, 6682, 6733, 6784, 6835, 6886, 6938, 6989, 7040, 7091, 7142, 7189, 7232, 7275, 7317, 7360, 7403, 7445, 7488, 7531, 7573, 7616, 7659 ]), 7679 * np.ones((53, )))) / 512 } parSteer = {'parent': parStrat, 'nDiscreteSteps': 9, 'steeringRange': 1.0} parCarrierSynth = { 'parent': parStrat, 'fModOn': .5, 'fModOff': 1.0, 'maxModDepth': 1.0, 'deltaPhaseMax': 0.5 } parMapper = { 'parent': parStrat, 'mapM': 500 * np.ones(16), 'mapT': 50 * np.ones(16), 'mapIdr': 60 * np.ones(16), 'mapGain': 0 * np.ones(16), 'mapClip': 2048 * np.ones(16), 'chanToElecPair': np.arange(16), 'carrierMode': 1 } parElectrodogram = { 'parent': parStrat, 'cathodicFirst': True, 'channelOrder': np.array( [1, 5, 9, 13, 2, 6, 10, 14, 3, 7, 11, 15, 4, 8, 12] ), # DO NOT CHANGE (different order of pulses will have no effect in vocoder output) 'enablePlot': True, 'outputFs': [], # DO NOT CHANGE (validation depends on matched output rate, vocoder would not produce different results at higher or lower Fs when parameters match accordingly) [default: [],(uses pulse width ~ 55555.55)] } parValidate = { 'parent': parStrat, 'lengthTolerance': 0.005, # maximum allowable difference in length between electrodogram and validation data, as a proportion of len(validationData) [0.5% default] 'saveIfSimilar': True, # save even if the are too similar to default strategy 'differenceThreshold': 1, 'maxSimilarChannels': 8, 'elGramFs': parElectrodogram[ 'outputFs'], # this is linked to the previous electrodogram generation step, it should always match [55556 Hz] 'outFile': None # This should be the full path including filename to a location where electrode matrix output will be saved after validation } results = {} #initialize demo results structure # read specified wav file and scale results['sig_smp_wavIn'], results['sourceName'] = readWavFunc( parReadWav ) # load the file specified in parReadWav; assume correct scaling in wav file (111.6 dB SPL peak full-scale) # apply preemphasis results['sig_smp_wavPre'] = tdFilterFunc( parPre, results['sig_smp_wavIn']) # preemphahsis # automatic gain control results['agc'] = dualLoopTdAgcFunc(parAgc, results['sig_smp_wavPre']) # agc # window and filter into channels results['sig_frm_audBuffers'] = winBufFunc( parWinBuf, results['agc']['wavOut']) # buffering results['sig_frm_fft'] = fftFilterbankFunc( parFft, results['sig_frm_audBuffers']) # stft results['sig_frm_hilbert'] = hilbertEnvelopeFunc( parHilbert, results['sig_frm_fft']) # get hilbert envelopes results['sig_frm_energy'] = channelEnergyFunc( parEnergy, results['sig_frm_fft'], results['agc']['smpGain']) # estimate channel energy # apply noise reduction results['sig_frm_gainNr'] = noiseReductionFunc( parNoiseReduction, results['sig_frm_energy'])[0] # estimate noise reduction results['sig_frm_hilbertMod'] = results['sig_frm_hilbert'] + results[ 'sig_frm_gainNr'] # apply noise reduction gains to envelope # subsample every third FFT input frame results['sig_3frm_fft'] = results['sig_frm_fft'][:, 2::3] # find spectral peaks results['sig_3frm_peakFreq'], results[ 'sig_3frm_peakLoc'] = specPeakLocatorFunc(parPeak, results['sig_3frm_fft']) # upsample back to full framerate (and add padding) results['sig_frm_peakFreq'] = np.repeat(np.repeat( results['sig_3frm_peakFreq'], 1, axis=0), 3, axis=1) results['sig_frm_peakFreq'] = np.concatenate((np.zeros( (results['sig_frm_peakFreq'].shape[0], 2)), results['sig_frm_peakFreq']), axis=1) results['sig_frm_peakFreq'] = results[ 'sig_frm_peakFreq'][:, :results['sig_frm_fft'].shape[1]] results['sig_frm_peakLoc'] = np.repeat(np.repeat( results['sig_3frm_peakLoc'], 1, axis=0), 3, axis=1) results['sig_frm_peakLoc'] = np.concatenate((np.zeros( (results['sig_frm_peakLoc'].shape[0], 2)), results['sig_frm_peakLoc']), axis=1) results['sig_frm_peakLoc'] = results[ 'sig_frm_peakLoc'][:, :results['sig_frm_fft'].shape[1]] # Calculate current steering weights and synthesize the carrier signals results['sig_frm_steerWeights'] = currentSteeringWeightsFunc( parSteer, results['sig_frm_peakLoc']) # steer current based on peak location results[ 'sig_ft_carrier'], results['sig_ft_idxFtToFrm'] = carrierSynthesisFunc( parCarrierSynth, results['sig_frm_peakFreq'] ) # carrier synthesis based on peak frequencies # map to f120 stimulation strategy results['sig_ft_ampWords'] = f120MappingFunc( parMapper, results[ 'sig_ft_carrier'], # combine envelopes, carrier, current steering weights and compute outputs results['sig_frm_hilbertMod'], results['sig_frm_steerWeights'], results['sig_ft_idxFtToFrm']) # convert amplitude words to simulated electrodogram for vocoder imput results['elGram'] = f120ElectrodogramFunc(parElectrodogram, results['sig_ft_ampWords']) # # load output of default processing strategy to compare with results['elGram'], return errors if data matrix is an invalid shape/unacceptable to the vocoder,save results['elGram'] to a file results['outputSaved'] = validateOutputFunc(parValidate, results['elGram'], results['sourceName']) # process electrodogram potentially saving as a file (change to saveOutput=True) results['audioOut'], results['audioFs'] = vocoderFunc(results['elGram'], saveOutput=False) return results
for file in os.listdir("./noise"): if file.endswith(".wav"): #Affects quality. Can be increased for better quality chunk = 2048 count = 0 # open up a wav wf = wave.open('noise/' + file, 'rb') CHANNELS = wf.getnchannels() RATE = wf.getframerate() swidth = wf.getsampwidth() m = MelBank.MelBank() # use a Blackman window window = np.blackman(chunk) data = wf.readframes(chunk) # play stream and find the frequency of each chunk while (len(data) == chunk * swidth): # unpack the data and times by the hamming window indata = np.array( wave.struct.unpack("%dh" % (len(data) / swidth), data)) * window # Take the fft and square each value fftData = abs(np.fft.rfft(indata))**2 #print(fftData) # find the maximum which = fftData[1:].argmax() + 1 # use quadratic interpolation around the max
import scipy.io as sio Num = sio.loadmat('lpf.mat') Num = Num['Num'] # open stream FORMAT = pyaudio.paInt16 CHANNELS = 1 RATE = 1024 CHUNK = int(4 * RATE) # RATE / number of updates per second RECORD_SECONDS = 300 # use a Blackman window window = np.blackman(CHUNK) x = 0 def soundPlot(stream): t1 = time.time() data = stream.read(CHUNK, exception_on_overflow=False) waveData = wave.struct.unpack("%dh" % (CHUNK), data) npArrayData = np.array(waveData) indata = lfilter(Num[0], 1, npArrayData) * window #indata = npArrayData*window #Plot time domain ax1.cla() ax1.plot(indata) ax1.grid()
def blackman(y): return np.blackman(y.shape[0])
def olf_bulb_10(Nmitral, H_in, W_in, P_odor_in, dam): # Nmitral = 10 #number of mitral cells Ngranule = np.copy(Nmitral) #number of granule cells pg. 383 of Li/Hop Ndim = Nmitral + Ngranule #total number of cells t_inh = 25 # time when inhalation starts t_exh = 205 #time when exhalation starts finalt = 395 # end time of the cycle #y = zeros(ndim,1); Sx = 1.43 #Sx,Sx2,Sy,Sy2 are parameters for the activation functions Sx2 = 0.143 Sy = 2.86 #These are given in Li/Hopfield pg 382, slightly diff in her thesis Sy2 = 0.286 th = 1 #threshold for the activation function tau_exh = 33.3333 #Exhale time constant, pg. 382 of Li/Hop exh_rate = 1 / tau_exh alpha = .15 #decay rate for the neurons #Li/Hop have it as 1/7 or .142 on pg 383 P_odor0 = np.zeros(Nmitral) #odor pattern, no odor H0 = H_in #weight matrix: to mitral from granule W0 = W_in #weights: to granule from mitral Ib = np.ones((Nmitral, 1)) * .243 #initial external input to mitral cells Ic = np.ones( (Ngranule, 1)) * .1 #initial input to granule cells, these values are #given on pg 382 of Li/Hop signalflag = 1 # 0 for linear output, 1 for activation function noise = np.zeros((Ndim, 1)) #noise in inputs noiselevel = .00143 noisewidth = 7 #noise correlation time, given pg 383 Li/Hop as 9, but 7 in thesis lastnoise = np.zeros((Ndim, 1)) #initial time of last noise pule #****************************************************************************** #CALCULATE FIXED POINTS #Calculating equilibrium value with no input rest0 = np.zeros((Ndim, 1)) restequi = fsolve(lambda x: equi(x,Ndim,Nmitral,Sx,Sx2,Sy,Sy2,th,alpha,\ t_inh,H0,W0,P_odor0,Ib,Ic,dam),rest0) #about 20 ms to run this np.random.seed(seed=23) #init0 = restequi+np.random.rand(Ndim)*.00143 #initial conditions plus some noise #for no odor input init0 = restequi + np.random.rand( Ndim) * .00143 #initial conditions plus some noise #for no odor input np.random.seed() #Now calculate equilibrium value with odor input lastnoise = lastnoise + t_inh - noisewidth #initialize lastnoise value #But what is it for? to have some #kind of correlation in the noise #find eigenvalues of A to see if input produces oscillating signal xequi = fsolve(lambda x: equi(x,Ndim,Nmitral,Sx,Sx2,Sy,Sy2,th,alpha,\ t_inh,H0,W0,P_odor_in,Ib,Ic,dam),rest0) #equilibrium values with some input, about 20 ms to run #****************************************************************************** #CALCULATE A AND DETERMINE EXISTENCE OF OSCILLATIONS diffgy = celldiff(xequi[Nmitral:], Sy, Sy2, th) diffgx = celldiff(xequi[0:Nmitral], Sx, Sx2, th) H1 = np.dot(H0, diffgy) W1 = np.dot(W0, diffgx) #intermediate step in constructing A A = np.dot(H1, W1) #Construct A dA, vA = lin.eig(A) #about 20 ms to run this #Find eigenvalues of A diff = (1j) * (dA)**.5 - alpha #criteria for a growing oscillation negsum = -(1j) * (dA)**.5 - alpha #Same diff_re = np.real(diff) #Take the real part negsum_re = np.real(negsum) #do an argmax to return the eigenvalue that will cause the fastest growing oscillations #Then do a spectrograph to track the growth of the associated freq through time indices = np.where( diff_re > 0) #Find the indices where the criteria is met indices2 = np.where(negsum_re > 0) #eigenvalues that could lead to growing oscillations # candidates = np.append(np.real((dA[indices])**.5),np.real((dA[indices2])**.5)) largest = np.argmax(diff_re) check = np.size(indices) check2 = np.size(indices2) if check == 0 and check2 == 0: # print("No Odor Recognized") dominant_freq = 0 else: dominant_freq = np.real((dA[largest])**.5) / ( 2 * np.pi) #find frequency of the dominant mode #Divide by 2pi to get to cycles/ms # print("Odor detected. Eigenvalues:",dA[indices],dA[indices2],\ # "\nEigenvectors:",vA[indices],vA[indices2],\ # "\nDominant Frequency:",dominant_freq) #************************************************************************* #SOLVE DIFFERENTIAL EQUATIONS TO GET INPUT AND OUTPUTS AS FN'S OF t #differential equation to solve teval = np.r_[0:finalt] #solve the differential equation sol = solve_ivp(lambda t,y: diffeq(t,y,Nmitral,Ngranule,Ndim,lastnoise,\ noise,noisewidth,noiselevel, t_inh,t_exh,exh_rate,alpha,Sy,\ Sy2,Sx,Sx2,th,H0,W0,P_odor_in,Ic,Ib,dam),\ [0,395],init0,t_eval = teval,method = 'RK45') t = sol.t y = sol.y y = np.transpose(y) yout = np.copy(y) #convert signal into output signal given by the activation fn if signalflag == 1: for i in np.arange(np.size(t)): yout[i, :Nmitral] = cellout(y[i, :Nmitral], Sx, Sx2, th) yout[i, Nmitral:] = cellout(y[i, Nmitral:], Sy, Sy2, th) #solve diffeq for P_odor = 0 #first, reinitialize lastnoise & noise noise = np.zeros((Ndim, 1)) lastnoise = np.zeros((Ndim, 1)) lastnoise = lastnoise + t_inh - noisewidth sol0 = sol = solve_ivp(lambda t,y: diffeq(t,y,Nmitral,Ngranule,Ndim,lastnoise,\ noise,noisewidth,noiselevel, t_inh,t_exh,exh_rate,alpha,Sy,\ Sy2,Sx,Sx2,th,H0,W0,P_odor0,Ic,Ib,dam),\ [0,395],init0,t_eval = teval,method = 'RK45') y0 = sol0.y y0 = np.transpose(y0) y0out = np.copy(y0) #convert signal into output signal given by the activation fn if signalflag == 1: for i in np.arange(np.size(t)): y0out[i, :Nmitral] = cellout(y0[i, :Nmitral], Sx, Sx2, th) y0out[i, Nmitral:] = cellout(y0[i, Nmitral:], Sy, Sy2, th) #***************************************************************************** #SIGNAL PROCESSING #Filtering the signal - O_mean: Lowpass fitered signal, under 20 Hz #S_h: Highpass filtered signal, over 20 Hz fs = 1 / (.001 * (t[1] - t[0])) #sampling freq, converting from ms to sec f_c = 15 / fs # Cutoff freq at 20 Hz, written as a ratio of fc to sample freq flter = np.sinc(2 * f_c * (t - (finalt - 1) / 2)) * np.blackman(finalt) #creating the #windowed sinc filter #centered at the middle #of the time data flter = flter / np.sum(flter) #normalize hpflter = -np.copy(flter) hpflter[int( (finalt - 1) / 2)] += 1 #convert the LP filter into a HP filter Sh = np.zeros(np.shape(yout)) Sl = np.copy(Sh) Sl0 = np.copy(Sh) Sbp = np.copy(Sh) for i in np.arange(Ndim): Sh[:, i] = np.convolve(yout[:, i], hpflter, mode='same') Sl[:, i] = np.convolve(yout[:, i], flter, mode='same') Sl0[:, i] = np.convolve(y0out[:, i], flter, mode='same') #find the oscillation period Tosc (Tosc must be greater than 5 ms to exclude noise) Tosc0 = np.zeros(np.size(np.arange(5, 50))) for i in np.arange(5, 50): Sh_shifted = np.roll(Sh, i, axis=0) Tosc0[i - 5] = np.sum( np.diagonal( np.dot(np.transpose(Sh[:, :Nmitral]), Sh_shifted[:, :Nmitral]))) #That is, do the correlation matrix (time correlation), take the diagonal to #get the autocorrelations, and find the max Tosc = np.argmax(Tosc0) Tosc = Tosc + 5 f_c2 = 1000 * ( 1.3 / Tosc) / fs #Filter out components with frequencies higher than this #to get rid of noise effects in cross-correlation #times 1000 to get units right flter2 = np.sinc(2 * f_c2 * (t - (finalt - 1) / 2)) * np.blackman(finalt) flter2 = flter2 / np.sum(flter2) for i in np.arange(Ndim): Sbp[:, i] = np.convolve(Sh[:, i], flter2, mode='same') #CALCULATE THE DISTANCE MEASURES #calculate phase via cross-correlation with each cell phase = np.zeros(Nmitral) for i in np.arange(1, Nmitral): crosscor = signal.correlate(Sbp[:, 0], Sbp[:, i]) tdiff = np.argmax(crosscor) - (finalt - 1) phase[i] = tdiff / Tosc * 2 * np.pi #Problem with the method below is that it will only give values from 0 to pi #for i in np.arange(1,Nmitral): # phase[i]=np.arccos(np.dot(Sbp[:,0],Sbp[:,i])/(lin.norm(Sbp[:,0])*lin.norm(Sbp[:,i]))) OsciAmp = np.zeros(Nmitral) Oosci = np.copy(OsciAmp) * 0j Omean = np.zeros(Nmitral) for i in np.arange(Nmitral): OsciAmp[i] = np.sqrt( np.sum(Sh[125:250, i]**2) / np.size(Sh[125:250, i])) Oosci[i] = OsciAmp[i] * np.exp(1j * phase[i]) Omean[i] = np.average(Sl[:, i] - Sl0[:, i]) Omean = np.maximum(Omean, 0) Ooscibar = np.sqrt(np.dot( Oosci, np.conjugate(Oosci))) / Nmitral #can't just square b/c it's complex Omeanbar = np.sqrt(np.dot(Omean, Omean)) / Nmitral maxlam = np.max(np.abs(np.imag(np.sqrt(dA)))) return yout, y0out, Sh, t, OsciAmp, Omean, Oosci, Omeanbar, Ooscibar, dominant_freq, maxlam
def plot(self, buf, bufsz, mode='eye'): BUFSZ = bufsz consumed = min(len(buf), BUFSZ - len(self.buf)) if len(self.buf) < BUFSZ: self.buf.extend(buf[:consumed]) return consumed self.plot_count += 1 if mode == 'eye' and self.plot_count % 20 != 0: self.buf = [] return consumed plots = [] s = '' while (len(self.buf)): if mode == 'eye': if len(self.buf) < self.sps: break for i in range(self.sps): s += '%f\n' % self.buf[i] s += 'e\n' self.buf = self.buf[self.sps:] plots.append('"-" with lines') elif mode == 'constellation': for b in self.buf: s += '%f\t%f\n' % (b.real, b.imag) s += 'e\n' self.buf = [] plots.append('"-" with points') elif mode == 'symbol': for b in self.buf: s += '%f\n' % (b) s += 'e\n' self.buf = [] plots.append('"-" with points') elif mode == 'fft' or mode == 'mixer': sum_pwr = 0.0 self.ffts = np.fft.fft( self.buf * np.blackman(BUFSZ)) / (0.42 * BUFSZ) self.ffts = np.fft.fftshift(self.ffts) self.freqs = np.fft.fftfreq(len(self.ffts)) self.freqs = np.fft.fftshift(self.freqs) tune_freq = (self.center_freq - self.relative_freq) / 1e6 if self.center_freq and self.width: self.freqs = ((self.freqs * self.width) + self.center_freq + self.offset_freq) / 1e6 for i in xrange(len(self.ffts)): if mode == 'fft': self.avg_pwr[i] = ( (1.0 - FFT_AVG) * self.avg_pwr[i]) + (FFT_AVG * np.abs(self.ffts[i])) else: self.avg_pwr[i] = ( (1.0 - MIX_AVG) * self.avg_pwr[i]) + (MIX_AVG * np.abs(self.ffts[i])) s += '%f\t%f\n' % (self.freqs[i], 20 * np.log10(self.avg_pwr[i])) if (mode == 'mixer') and (self.avg_pwr[i] > 1e-5): if (self.freqs[i] - self.center_freq) < 0: sum_pwr -= self.avg_pwr[i] elif (self.freqs[i] - self.center_freq) > 0: sum_pwr += self.avg_pwr[i] self.avg_sum_pwr = ( (1.0 - BAL_AVG) * self.avg_sum_pwr) + (BAL_AVG * sum_pwr) s += 'e\n' self.buf = [] plots.append('"-" with lines') self.buf = [] # FFT processing needs to be completed to maintain the weighted average buckets # regardless of whether we actually produce a new plot or not. if self.plot_interval and self.last_plot + self.plot_interval > time.time( ): return consumed self.last_plot = time.time() filename = None if self.output_dir: if self.sequence >= 2: delete_pathname = '%s/plot-%s-%d.png' % (self.output_dir, mode, self.sequence - 2) if os.access(delete_pathname, os.W_OK): os.remove(delete_pathname) h = 'set terminal png\n' filename = 'plot-%s-%d.png' % (mode, self.sequence) self.sequence += 1 h += 'set output "%s/%s"\n' % (self.output_dir, filename) else: h = 'set terminal x11 noraise\n' #background = 'set object 1 circle at screen 0,0 size screen 1 fillcolor rgb"black"\n' #FIXME! background = '' h += 'set key off\n' if mode == 'constellation': h += background h += 'set size square\n' h += 'set xrange [-1:1]\n' h += 'set yrange [-1:1]\n' h += 'set title "%sConstellation"\n' % self.plot_name elif mode == 'eye': h += background h += 'set yrange [-4:4]\n' h += 'set title "%sDatascope"\n' % self.plot_name elif mode == 'symbol': h += background h += 'set yrange [-4:4]\n' h += 'set title "%sSymbol"\n' % self.plot_name elif mode == 'fft' or mode == 'mixer': h += 'unset arrow; unset title\n' h += 'set xrange [%f:%f]\n' % (self.freqs[0], self.freqs[len(self.freqs) - 1]) h += 'set xlabel "Frequency"\n' h += 'set ylabel "Power(dB)"\n' h += 'set grid\n' h += 'set yrange [-100:0]\n' if mode == 'mixer': # mixer h += 'set title "%sMixer: balance %3.0f (smaller is better)"\n' % ( self.plot_name, (np.abs(self.avg_sum_pwr * 1000))) else: # fft h += 'set title "%sSpectrum"\n' % self.plot_name if self.center_freq: arrow_pos = (self.center_freq - self.relative_freq) / 1e6 h += 'set arrow from %f, graph 0 to %f, graph 1 nohead\n' % ( arrow_pos, arrow_pos) h += 'set title "%sSpectrum: tuned to %f Mhz"\n' % ( self.plot_name, arrow_pos) dat = '%splot %s\n%s' % (h, ','.join(plots), s) self.gp.poll() if self.gp.returncode is None: # make sure gnuplot is still running try: self.gp.stdin.write(dat) except (IOError, ValueError): pass if filename: self.filename = filename return consumed
p_time = pulses["time"][:] time = observables["time"][1:] num_dims = f["Parameters"]["num_dims"][0] num_electrons = f["Parameters"]["num_electrons"][0] num_pulses = f["Parameters"]["num_pulses"][0] checkpoint_frequency = f["Parameters"]["write_frequency_observables"][0] energy = f["Parameters"]["energy"][0] for elec_idx in range(num_electrons): for dim_idx in range(num_dims): if (not (dim_idx == 0 and f["Parameters"]["coordinate_system_idx"][0] == 1)): data = observables[ "dipole_acceleration_" + str(elec_idx) + "_" + str(dim_idx)][1:len(pulses["field_" + str(dim_idx)][ checkpoint_frequency::checkpoint_frequency]) + 1] data = data * np.blackman(data.shape[0]) padd2 = 2**np.ceil(np.log2(data.shape[0] * 4)) paddT = np.max(time) * padd2 / data.shape[0] dH = 2 * np.pi / paddT / energy if np.max(data) > 1e-19: data = np.absolute( np.fft.fft( np.lib.pad( data, (int(np.floor((padd2 - data.shape[0]) / 2)), int(np.ceil((padd2 - data.shape[0]) / 2))), 'constant', constant_values=(0.0, 0.0)))) if count == 0: count = 1 harm_value = data[np.argmin(
import numpy as np import matplotlib.pyplot as plt from scipy.fftpack import fft, fftshift import sys sys.path.append('../../../software/models/') import utilFunctions as UF (fs, x) = UF.wavread('../../../sounds/soprano-E4.wav') N = 1024 x1 = np.blackman(N) * x[40000:40000 + N] plt.figure(1, figsize=(9.5, 6)) X = np.array([]) x2 = np.zeros(N) plt.subplot(4, 1, 1) plt.title('x (soprano-E4.wav)') plt.plot(x1, lw=1.5) plt.axis([0, N, min(x1), max(x1)]) X = fft(fftshift(x1)) mX = 20 * np.log10(np.abs(X[0:N // 2])) pX = np.angle(X[0:N // 2]) plt.subplot(4, 1, 2) plt.title('mX = magnitude spectrum') plt.plot(mX, 'r', lw=1.5) plt.axis([0, N / 2, min(mX), max(mX)]) plt.subplot(4, 1, 3)
ax2.set_title("result") resCplx = sps.hilbert(results) ax3 = fig1.add_subplot(223) ax3.plot(abs(resCplx)) ax3.grid() ax3.set_title("result amplitude") ax4 = fig1.add_subplot(224) ax4.plot( np.cumsum(np.unwrap(np.diff(np.angle(resCplx)) - (2 * np.pi) / ratio))) ax4.grid() ax4.set_title("result angle (shout change by 2pi)") wndw = np.blackman(results.size) pwr = 20 * np.log10( abs(np.fft.fft(results * wndw / np.average(wndw))) / sample) frq = np.linspace(0, 1, pwr.size) fig3 = plt.figure() ax5 = fig3.add_subplot(211) ax5.plot(frq[1:4096], pwr.reshape((pwr.size, 1))[1:4096]) ax5.grid() ax5.set_xlabel("Frequency [Fs]") ax5.set_ylabel("Amplitude [dB]") ax5.set_title("Output Spectrum") res = PsiFixGetBitsAsInt(results, outFmt) # text file used to make VHDL testbench comparison np.savetxt(STIM_DIR + '/model_result_IQmod.txt',
import numpy as np import matplotlib.pyplot as plt from scipy.signal import hamming, triang, blackmanharris import math import sys, os, functools, time sys.path.append( os.path.join(os.path.dirname(os.path.realpath(__file__)), '../../../software/models/')) import dftModel as DFT import utilFunctions as UF (fs, x) = UF.wavread('../../../sounds/carnatic.wav') pin = int(1.4 * fs) w = np.blackman(1601) N = 4096 hM1 = (w.size + 1) // 2 hM2 = w.size // 2 x1 = x[pin - hM1:pin + hM2] mX, pX = DFT.dftAnal(x1, w, N) plt.figure(1, figsize=(9, 7)) plt.subplot(311) plt.plot(np.arange(-hM1, hM2) / float(fs), x1, lw=1.5) plt.axis([-hM1 / float(fs), hM2 / float(fs), min(x1), max(x1)]) plt.title('x (carnatic.wav)') plt.subplot(3, 1, 2) plt.plot(fs * np.arange(mX.size) / float(N), mX, 'r', lw=1.5) plt.axis([0, fs / 4, -100, max(mX)]) plt.title('mX')
popt = curve_fit(func, ion_V, ion_I) a = popt[0][0] b = popt[0][1] I_i = a * IV[:, 0] + b # Ion current I_noni = IV[:, 1] - I_i I_noni = I_noni.reshape( (len(I_noni), 1)) # reshaping means transpose of matrix I_noni = I_noni.clip(min=0) # IV curve Subtracted ion current IV = np.hstack([IV, I_noni]) ## Getting lpe for 1st derivative & noise amplitude M = 21 w = np.blackman(M) / sum(np.blackman(M)) dI_dV = np.gradient(IV[:, 1], h) dI_dV = np.nan_to_num(dI_dV) mov_avg = signal.filtfilt(w, 1, dI_dV) id_Vp = np.nanargmax(mov_avg) Vp = float(IV[id_Vp, 0]) # Plasma Potential Ie = float(IV[id_Vp, 2]) # Electron saturation current Noise_amp_abs = float( (max(I_noni[int(id_V_ion_1[0]):int(id_V_ion_2[0])] - min(I_noni[int(id_V_ion_1[0]):int(id_V_ion_2[0])]))) / 2) Noise_amp = Noise_amp_abs / float(I_noni[id_Vp]) Noise = Noise_amp * (np.random.rand(n, 1) - 0.5) ## Finding Electron Temperature, Te # Te is determined by floating potential and the difference with plasma potential ln_I = np.log(I_noni[:, 0])
def update(self, evt): try: f0 = 1000 signal_rms = 1 Fs = to_float(self.text_ctrl_fs.GetValue()) * 1e3 LDF = to_float(self.text_ctrl_ldf.GetValue()) # TEMPORAL ------------------------------------------------------------------------------------------------- N = getWindowLength(f0, 200e3, windfunc='blackman', error=LDF, mainlobe_type='absolute') self.x, self.y = ADC(signal_rms, f0, 200e3, N, CONTAINS_HARMONICS, CONTAINS_NOISE) N = getWindowLength(f0, Fs, windfunc='blackman', error=LDF, mainlobe_type='absolute') xdt, ydt = ADC(signal_rms, f0, Fs, N, CONTAINS_HARMONICS, CONTAINS_NOISE) rms_true = round( true_signal(signal_rms, N, CONTAINS_HARMONICS, CONTAINS_NOISE), 8) rms_sampled = round(rms_flat(ydt), 8) rms_delta = round(1e6 * (rms_true - rms_sampled), 2) cycles = N * f0 / Fs samples_per_cycles = N / cycles # ALIASING ------------------------------------------------------------------------------------------------- aliased_freq = [1.0, 3.0, 5.0] for idx, harmonic in enumerate(aliased_freq): # https://ez.analog.com/partnerzone/fidus-partnerzone/m/file-uploads/212 Fn = Fs / 2 nyquist_zone = np.floor(f0 * harmonic / Fn) + 1 if nyquist_zone % 2 == 0: aliased_freq[idx] = (Fn - (f0 * harmonic % Fn)) / 1000 else: aliased_freq[idx] = (f0 * harmonic % Fn) / 1000 # WINDOW --------------------------------------------------------------------------------------------------- w = np.blackman(N) # Calculate amplitude correction factor after windowing ---------------------------------------------------- # https://stackoverflow.com/q/47904399/3382269 amplitude_correction_factor = 1 / np.mean(w) # Calculate the length of the FFT -------------------------------------------------------------------------- if (N % 2) == 0: # for even values of N: FFT length is (N / 2) + 1 fft_length = int(N / 2) + 1 else: # for odd values of N: FFT length is (N + 1) / 2 fft_length = int((N + 2) / 2) # SPECTRAL ------------------------------------------------------------------------------------------------- xf_fft = np.round(np.fft.fftfreq(N, d=1. / Fs), 6) yf_fft = (np.fft.fft(ydt * w) / fft_length) * amplitude_correction_factor yf_rfft = yf_fft[:fft_length] xf_rfft = np.round(np.fft.rfftfreq(N, d=1. / Fs), 6) # one-sided if aliased_freq[0] == 0: fh1 = f0 else: fh1 = 1000 * aliased_freq[0] self.plot(fh1, xdt, ydt, fft_length, xf_rfft, yf_rfft) self.results_update(N, rms_true, rms_sampled, rms_delta, np.floor(cycles), samples_per_cycles, aliased_freq) except ValueError as e: self.popup_dialog(e)
def plot_activations_density(z_hat, n_times_atom, sfreq=1., threshold=0.01, bandwidth='auto', axes=None, t_min=0, plot_activations=False, colors=None): """ Parameters ---------- z_hat : array, shape (n_atoms, n_trials, n_times_valid) The sparse activation matrix. n_times_atom : int The support of the atom. sfreq : float Sampling frequency threshold : float Remove activations (normalized with the max) below this threshold bandwidth : float, array of float, or 'auto' Bandwidth (in sec) of the kernel axes : array of axes, or None Axes to plot into t_min : float Time offset for the xlabel display plot_activations : boolean If True, the significant activations are plotted as black dots colors : list of matplotlib compatible colors Colors of the plots """ n_atoms, n_trials, n_times_valid = z_hat.shape # sum activations over all trials z_hat_sum = z_hat.sum(axis=1) if bandwidth == 'auto': bandwidth = n_times_atom if axes is None: fig, axes = plt.subplots(n_atoms, num='density', figsize=(8, 2 + n_atoms * 3)) axes = np.atleast_1d(axes) if colors is None: colors = itertools.cycle(COLORS) for ax, activations, color in zip(axes.ravel(), z_hat_sum, colors): ax.clear() time_instants = np.arange(n_times_valid) / float(sfreq) + t_min selection = activations > threshold * z_hat_sum.max() n_elements = selection.sum() if n_elements == 0: ax.plot(time_instants, np.zeros_like(time_instants)) continue # plot the activations as black dots if plot_activations: ax.plot(time_instants[selection], activations[selection] / activations[selection].max(), '.', color='k') window = np.blackman(bandwidth) smooth_activations = np.convolve(activations, window, 'same') ax.fill_between(time_instants, smooth_activations, color=color, alpha=0.5) return axes
# Plot horizontal line SmoothingStep = 50 plt.figure(2) plt.imshow(Image) plt.title('Select line to plot') HorizontalLine = int(round(plt.ginput(1)[0][1])) plt.hlines(HorizontalLine, 0, Image.shape[1], 'r', linewidth=3) plt.subplot(211) plt.imshow(Image) plt.hlines(HorizontalLine, 0, Image.shape[1], 'r', linewidth=3) plt.title('Original') plt.subplot(212) plt.plot(Image[HorizontalLine, :], label='Line ' + str(HorizontalLine)) window = numpy.blackman(SmoothingStep) smoothed = numpy.convolve(window / window.sum(), Image[HorizontalLine, :], mode='same') plt.plot(range(SmoothingStep, len(smoothed) - SmoothingStep), smoothed[SmoothingStep:-SmoothingStep], 'r--', linewidth=5, label='smoothed (by ' + str(SmoothingStep) + ')') plt.xlim((0, Image.shape[1])) plt.legend(loc='best') plt.draw() if options.MTF: print 'calculating MTF of', os.path.basename(options.Filename) # http://is.gd/V3XClS # Modulation (contrast) = (Imax - Imin) / (Imax + Imin) if options.SNR:
def init(self, serial_port): global is_OPS241_OPS242_A global is_OPS241_OPS242_B global is_OPS243_A global is_OPS243_C global is_doppler global is_fmcw global invert_i_values global sample_count global NFFT self.serial_port = serial_port # Initialize and query Ops24x Module print("\nInitializing Ops24x Module") send_OPS24x_cmd(serial_port, "\nSet Power Idle Mode: ", OPS24x_Power_Idle) is_OPS241_OPS242_A = False is_OPS241_OPS242_B = False is_OPS243_A = False is_OPS243_C = False rtn_val = send_OPS24x_cmd(serial_port, "\nQuery for Product: ", OPS24x_Query_Product, "Product") if rtn_val.find("243") >= 0: if rtn_val.find("oppler") >= 0: is_OPS243_A = True elif rtn_val.find("ombo") >= 0: is_OPS243_C = True elif rtn_val.find("OPS243-C") >= 0: is_OPS243_C = True else: if rtn_val.find("oppler") >= 0: is_OPS241_OPS242_A = True elif rtn_val.find("FMCW") >= 0: is_OPS241_OPS242_B = True is_fmcw = False is_doppler = False if options.is_doppler: is_doppler = True elif options.is_fmcw: is_doppler = False else: if is_OPS241_OPS242_A or is_OPS243_A: is_doppler = True else: is_doppler = False invert_i_values = False if is_OPS241_OPS242_A or is_OPS241_OPS242_B: invert_i_values = True if is_OPS241_OPS242_A or is_OPS243_A: send_OPS24x_cmd(serial_port, "\nSet no binary data: ", OPS24x_Output_No_Binary_data) if is_doppler: send_OPS24x_cmd(serial_port, "\nSet Send Speed report: ", OPS24x_Output_Speed) else: send_OPS24x_cmd(serial_port, "\nSet No Speed report: ", OPS24x_Output_No_Speed) if is_OPS243_C: if is_doppler: send_OPS24x_cmd(serial_port, "\nSet No Distance report: ", OPS24x_Output_No_Distance) send_OPS24x_cmd(serial_port, "\nSet yes CW Magnitudes: ", OPS24x_Output_CW_Mag) else: is_fmcw = True send_OPS24x_cmd(serial_port, "\nSet Send Distance report: ", OPS24x_Output_Distance) send_OPS24x_cmd(serial_port, "\nSet yes FMCW Magnitudes: ", OPS24x_Output_FMCW_Mag) else: send_OPS24x_cmd(serial_port, "\nSet yes Magnitudes: ", OPS24x_Output_CW_Mag) sample_count = 512 NFFT = 1024 if is_doppler: print("Sending CW sampling rate and size:", options.power_letter) send_OPS24x_cmd(serial_port, "\nSet OPS24x CW Frequency: ", OPS24x_CW_Sampling_Freq10) sample_count = 512 NFFT = 512 send_OPS24x_cmd(serial_port, "\nSet OPS24x CW Data Size: ", OPS24x_CW_Sampling_Size512) if is_OPS243_C: send_OPS24x_cmd(serial_port, "\nSet OPS24x CW FFT Scale: ", OPS24x_CW_FFT_Scale1) else: print("Sending FMCW sampling rate and size:", options.power_letter) send_OPS24x_cmd(serial_port, "\nSet OPS24x FMCW Frequency: ", 's=320') sample_count = 512 NFFT = 1024 send_OPS24x_cmd(serial_port, "\nSet OPS24x FMCW Data Size: ", OPS24x_FMCW_Sampling_Size512) if is_OPS243_C: send_OPS24x_cmd(serial_port, "\nSet OPS24x FMCW FFT Scale: ", OPS24x_FMCW_FFT_Scale2) global hann_window global blackman_window hann_window = np.hanning(sample_count) blackman_window = np.blackman(sample_count) if options.low_cutoff != ' ': print("Low cutoff:", options.low_cutoff) fft_bin_low_cutoff = int(options.low_cutoff) send_OPS24x_cmd(serial_port, "\nSet yes JSONy data: ", OPS24x_Output_JSONy_data, "utputFeature") if options.plot_I or options.plot_Q or options.plot_IQ_and_local_FFT or options.plot_IQ_only or options.plot_IQ_FFT: if is_doppler: send_OPS24x_cmd(serial_port, "\nSet yes CW Raw data: ", OPS24x_Output_CW_Raw) if is_OPS243_C: send_OPS24x_cmd(serial_port, "\nSet no FMCW Raw data: ", OPS24x_Output_No_FMCW_Raw) else: if is_OPS243_C: send_OPS24x_cmd(serial_port, "\nSet yes FMCW Raw data: ", OPS24x_Output_FMCW_Raw) send_OPS24x_cmd(serial_port, "\nSet no CW Raw data: ", OPS24x_Output_No_CW_Raw) else: send_OPS24x_cmd(serial_port, "\nSet yes FMCW Raw data: ", OPS24x_Output_CW_Raw) else: send_OPS24x_cmd(serial_port, "\nSet no CW Raw data: ", OPS24x_Output_No_CW_Raw) if is_OPS243_C: send_OPS24x_cmd(serial_port, "\nSet no FMCW Raw data: ", OPS24x_Output_No_FMCW_Raw) if options.plot_FFT or options.plot_IQ_FFT: if is_doppler: send_OPS24x_cmd(serial_port, "\nSet yes CW FFT data: ", OPS24x_Output_CW_FFT) if is_OPS243_C: send_OPS24x_cmd(serial_port, "\nSet no FMCW FFT data: ", OPS24x_Output_No_FMCW_FFT) else: if is_OPS243_C: send_OPS24x_cmd(serial_port, "\nSet yes FMCW FFT data: ", OPS24x_Output_FMCW_FFT) send_OPS24x_cmd(serial_port, "\nSet no CW FFT data: ", OPS24x_Output_No_CW_FFT) else: send_OPS24x_cmd(serial_port, "\nSet yes FMCW FFT data: ", OPS24x_Output_CW_FFT) else: send_OPS24x_cmd(serial_port, "\nSet no CW FFT data: ", OPS24x_Output_No_CW_FFT) if is_OPS243_C: send_OPS24x_cmd(serial_port, "\nSet no FMCW FFT data: ", OPS24x_Output_No_FMCW_FFT) if options.wait_letter != ' ': print("Sending wait argument:", options.wait_letter) send_OPS24x_cmd(serial_port, "\nSet OPS24x Wait ?: ", "W" + options.wait_letter) if options.power_letter != ' ': print("Sending power argument:", options.power_letter) send_OPS24x_cmd(serial_port, "\nSet OPS24x Power: ", "P" + options.power_letter) send_OPS24x_cmd(serial_port, "\nSet Power Active Mode: ", OPS24x_Power_Active, "PowerMode")
from scipy.signal import hamming, hanning, triang, blackmanharris, resample import math import sys, os, time sys.path.append( os.path.join(os.path.dirname(os.path.realpath(__file__)), '../../../software/models/')) import stft as STFT import utilFunctions as UF import harmonicModel as HM (fs, x) = UF.wavread( os.path.join(os.path.dirname(os.path.realpath(__file__)), '../../../sounds/flute-A4.wav')) w = np.blackman(551) N = 1024 t = -100 nH = 40 minf0 = 420 maxf0 = 460 f0et = 5 maxnpeaksTwm = 5 minSineDur = .1 harmDevSlope = 0.01 Ns = 512 H = Ns // 4 mX, pX = STFT.stftAnal(x, w, N, H) hfreq, hmag, hphase = HM.harmonicModelAnal(x, fs, w, N, H, t, nH, minf0, maxf0, f0et, harmDevSlope, minSineDur)
def spectral_analysis(dx, Ain, tapering=None, overlap=None, wsize=None, alpha=3.0, detrend=False, normalise=False, integration=True, average=True, ARspec=None): """ Spectral_Analysis : This function performs a spatial spectral analysis with different options on a time series of SLA profiles. :parameter dx: sampling distance :parameter Ain: 2D table of sla data with time along 2nd axis (NXxNT with NX the spatial length and NT the time length) :keyword tapering: apply tapering to the data * If this keyword is of type bool : apply hamming window. * If this keyword is a string : apply a hamming ('hamm'), hann ('hann'), kaiser-bessel ('kaiser'), kaiser-bessel ('blackman') or no ('none') tapering function. * If this keyword is an :class:`numpy.array` object : apply this array as taper. :keyword overlap: overlap coefficient of the windows (0.75 means 75% overlap). :keyword wsize: size of the sub-segments. :keyword normalise: If True, normalise the spectrum by its overall energy content. :keyword detrend: If True, removes a linear trend to the segmented signal (if tapered) or to the whole signal (if not tapered). :keyword integration: If True, integrate the spectrum between 2 frequencies. :keyword alpha: used to compute the input (beta) of the kaiser-bessel taper. :keyword ARspec: Applies an Auto-Regression model of the order provided as value of this parameter. :return: a spectrum structure .. code-block:: python {'esd':esd, #Energy Spectral Density 'psd':psd, #Power Spectral Density 'fq':fq, #frequency 'p':p, #wavelength 'params':params} #tapering parameters. :author: Renaud DUSSURGET (RD) - LER/PAC, Ifremer :change: Created by RD, December 2012 """ A = Ain.copy() #Check dimensions sh = A.shape ndims = len(sh) N = sh[0] #Time series are found along the last dimension #If vector, add one dimension if ndims == 1: A = A.reshape((N, 1)) sh = A.shape ndims = len(sh) nr = sh[1] #Number of repeats nt = nr # gain=1.0 #Scaling gain... (used for tapering issues) # #Get the overall energy # spec=get_spec(dx, A[:,0]) # F=spec['fq'] # Eref = ((A[:,0]-A[:,0].mean())**2).sum() #Get the reference energy level # ESDref=spec['esd'] # SFactor=Eref/spec['esd'].sum() # ESDref*=SFactor # PSDref=spec['psd']*SFactor # print 'Check parseval theorem : SUM|Y(f)|²={0}, SUM|y(t)|²={1}'.format(spec['esd'].sum(),((A[:,0]-A[:,0].mean())**2).sum()) #Apply tapering if asked ######################## if tapering is not None: #Set tapering defaults overlap = 0 if overlap is None else overlap wsize = N if wsize is None else wsize #Get time splitting (tapering) parameters ######################################### a = np.float32(wsize) b = np.float32(overlap) c = np.float32(N) nn = np.floor( (c - (a * b)) / (a - (a * b))) #This is the number of segments print 'Number of windows :{0}\nTotal windowed points : {1} ({2} missing)\nTotal points : {3}'.format( nn, nn * wsize, N - nn * wsize * overlap, N) ix = np.arange(nn) * ( (1.0 - b) * a) #These are the starting points of each segments #Moving window ############## dum = np.zeros((wsize, nn, nr), dtype=np.float64) for j in np.arange(nr): for i in np.arange( nn): #looping through time to get splitted time series dum[:, i, j] = detrend_fun( np.arange(wsize), A[ix[i]:ix[i] + wsize, j]) if detrend else A[ix[i]:ix[i] + wsize, j] #Set up tapering window ####################### beta = np.pi * alpha hamm = np.hamming(wsize) hann = np.hanning(wsize) kbess = np.kaiser(wsize, beta) blackman = np.blackman(wsize) notaper = np.ones(wsize) #overpass tapering option gain = 1.0 if isinstance(tapering, bool): which = 'hamm' elif isinstance(tapering, str): if tapering.upper() == 'HAMMING': which = 'hamm' gain = np.sum(hamm) / wsize #0.530416666667 elif tapering.upper() == 'HANNING': which = 'hann' gain = np.sum(hann) / wsize #0.489583333333 elif tapering.upper() == 'KAISER': which = 'kbess' gain = np.sum(kbess) / wsize #0.394170357504 elif tapering.upper() == 'NONE': which = 'notaper' gain = 1.0 elif tapering.upper() == 'BLACKMAN': which = 'blackman' gain = np.sum(blackman) / wsize else: raise Exception('Unknown taper {0}'.format(tapering)) elif isinstance(tapering, np.ndarray): which = 'tapering' gain = np.sum(tapering) / wsize else: raise Exception('Bad value for tapering keyword') exec('window=' + which) window = np.repeat(window, nn * nr).reshape((wsize, nn, nr)) #Apply tapering on segmented data A = dum.copy() * window A = A.reshape(wsize, nr * nn) #Reshapa matrix nr = nn * nr else: if detrend: for i in np.arange(nr): A[:, i] = detrend_fun(np.arange(N), A[:, i]) if detrend else A[:, i] gain = 1.0 #Run transform ############### for i in np.arange(nr): if ARspec is not None: spec = yule_walker_regression(dx, A[:, i], ARspec) else: spec = get_spec(dx, A[:, i], integration=integration, gain=gain) if i == 0: esd = spec['esd'] psd = spec['psd'] fq = spec['fq'] phase = spec['phase'] if ARspec: model = spec['psd'].model else: esd = np.append(esd, spec['esd']) psd = np.append(psd, spec['psd']) phase = spec['phase'] if ARspec: model = np.append(model, spec['psd'].model) # factor=((A[:,0]-A[:,0].mean())**2).sum()/spec['esd'].sum() #Average spectrum ################# nf = len(fq) p = 1. / fq esd = esd.reshape(nr, nf) psd = psd.reshape(nr, nf) if average: esd = (np.sum(esd, axis=0) / nr) #/gain psd = (np.sum(psd, axis=0) / nr) #/gain psd = psd * (gain**0.5) # print gain, np.sqrt(gain), gain **2, gain*0.5, gain/2. # esd=(np.sum(esd,axis=0))#/gain # psd=(np.sum(psd,axis=0))#/gain if ARspec: mparam, msig = zip(*tuple([(el['parameters'], el['sig']) for el in model])) deg = ARspec mparam = np.concatenate(mparam).reshape((len(model), deg)) msig = np.array(msig) if average: mparam = mparam.mean(axis=0) msig = np.nansum(msig) / msig.size mstr = {'parameters': mparam, 'sig': msig, 'n': N, 'deg': ARspec} setattr(esd, 'model', mstr) setattr(psd, 'model', mstr) #Normalise by energy content Scaling_Factor = len(fq) / esd.sum() if normalise: esd *= Scaling_Factor psd *= Scaling_Factor if tapering is not None: return { 'params': { 'tapering': tapering is not None, 'which': which, 'wsize': int(wsize), 'nwind': int(nn), 'overlap': int(100. * overlap), 'gain': gain }, 'psd': psd, 'esd': esd, 'fq': fq, 'p': p, 'phase': phase } else: return { 'params': { 'tapering': tapering is not None }, 'psd': psd, 'esd': esd, 'fq': fq, 'p': p, 'phase': phase }
def bloop(): pitches = [sf.mtof(60), sf.mtof(64), sf.mtof(66), sf.mtof(67), sf.mtof(69), sf.mtof(70), sf.mtof(72)] choice = np.random.randint(len(pitches)) length = int(fs*0.05) return sf.osc(np.ones(length) * pitches[choice], sampling_rate=fs) * np.blackman(length)