def seperable_gaussian_convolution(): F = plt.imread('../images/cameraman.png') # Example of Gaussian convolution. s = 3 G = convolve1d(F, Gauss1(s), axis=-1, mode='nearest') G = convolve1d(G, Gauss1(s), axis=0, mode='nearest') plt.subplot(1, 2, 1) plt.imshow(F, cmap=plt.cm.gray) plt.subplot(1, 2, 2) plt.imshow(G, cmap=plt.cm.gray) plt.show() # Gaussian convolution function run 100 times for average execution time. n = 10 s_values = np.array([1, 2, 3, 5, 7, 9, 11, 15, 19]) times = avg_runnning(F, s_values, n) times2d = gauss2d.avg_runnning(F, s_values, n) plt.clf() plt.title("Average execution time versus the scale\n(run {0} times)" .format(n)) plt.xlabel("s") plt.ylabel("time (ms)") plt.plot(s_values, times, label="1d convolution") plt.plot(s_values, times2d, label="2d convolution") plt.legend() plt.show()
def move_nanvar_filter(arr, window, axis=-1): "Moving window variance ignoring NaNs, implemented with a filter." arr = np.array(arr, copy=False) global convolve1d if convolve1d is None: try: from scipy.ndimage import convolve1d except ImportError: raise ValueError("'filter' method requires SciPy.") if axis is None: raise ValueError("An `axis` value of None is not supported.") if window < 1: raise ValueError("`window` must be at least 1.") if window > arr.shape[axis]: raise ValueError("`window` is too long.") arr = arr.astype(float) nrr = np.isnan(arr) arr[nrr] = 0 nrr = nrr.astype(int) w = np.ones(window, dtype=int) x0 = (1 - window) // 2 convolve1d(nrr, w, axis=axis, mode="constant", cval=0, origin=x0, output=nrr) y = convolve1d(arr, w, axis=axis, mode="constant", cval=np.nan, origin=x0) y /= window - nrr y *= y arr *= arr convolve1d(arr, w, axis=axis, mode="constant", cval=np.nan, origin=x0, output=arr) arr /= window - nrr arr -= y arr[nrr == window] = np.nan return arr
def second_derivatives(array, smooth=2): """ Compute the second derivatives of all dimensions pairs of the input array :Inputs: array: any ndarray smooth: the second derivative are computed by convolving the input array by [1,-2,1]. The smooth parameter set how many times this basic filter is convoluted with [1,2,1]/2, which smooth it. :Output: Return a tuple of the second derivative arrays in the order (where dd_ij is the the second derivative d2(array)/didj for a N-dimensional array): (dd_00, dd_01, ..., dd_0N, dd_11, dd_12, ..., dd_1N, ..., dd_N-1N, dd_NN) :Example: for 3d array 'volume_array' dv_00, dv_01, dv_02, dv_11, dv_12, dv_22 = second_derivatives(volume_array) See also: numpy.gradient """ # compute the derivative filter dd = [1,-1] for i in xrange(smooth): dd = _np.convolve(dd,[1,2,1])/2. # compute the second derivatives res = () for i in xrange(array.ndim): tmp = _nd.convolve1d(array,dd,axis=i) for j in xrange(i,array.ndim): res += _nd.convolve1d(tmp,dd,axis=j), return res
def unsharp_masking(X): lp = np.array(X) for i, ws in zip([0, 1, 2], [50, 50, 25]): h = hamming(ws) h /= h.sum() convolve1d(lp, h, axis=i, output=lp) return X - lp
def conv_2_sep_Y_circ(self,image,xkernel,thetakernel):#,upsample=10): # up_image = np.repeat(image,upsample) # x_convolved = ndimage.convolve1d(image,xkernel,mode='mirror',axis=1) # both_convolved = ndimage.convolve1d(x_convolved,thetakernel,mode='mirror',axis=0) x_convolved = ndimage.convolve1d(image,xkernel,mode='constant',axis=1) both_convolved = ndimage.convolve1d(x_convolved,thetakernel,mode='wrap',axis=0) return both_convolved
def move_var_filter(arr, window, axis=-1): "Moving window variance implemented with a filter." global convolve1d if convolve1d is None: try: from scipy.ndimage import convolve1d except ImportError: raise ValueError("'filter' method requires SciPy.") if axis == None: raise ValueError, "An `axis` value of None is not supported." if window < 1: raise ValueError, "`window` must be at least 1." if window > arr.shape[axis]: raise ValueError, "`window` is too long." arr = arr.astype(float) w = np.empty(window) w.fill(1.0 / window) x0 = (1 - window) // 2 y = convolve1d(arr, w, axis=axis, mode='constant', cval=np.nan, origin=x0) y *= y arr *= arr convolve1d(arr, w, axis=axis, mode='constant', cval=np.nan, origin=x0, output=arr) arr -= y return arr
def extract_oriented_patches2D( img, r, coordinates, nb_proj=100 ): img = img.astype('float64') projection_matrix = np.zeros( (nb_proj,2), dtype='float64' ) for i in xrange(nb_proj): theta = float(i) * 2.0 * math.pi / nb_proj projection_matrix[i,0] = math.sin(theta) projection_matrix[i,1] = math.cos(theta) print "computing gradients..." # grad = np.dstack( ( nd.sobel( img, mode='constant', axis=0 ), # nd.sobel( img, mode='constant', axis=1 ) ) ) grad = np.dstack( ( nd.convolve1d( img, [-1,1], mode='constant', axis=0 ), nd.convolve1d( img, [-1,1], mode='constant', axis=1 ) ) ) print "projecting gradients..." hist = _patches.project_gradients2D( grad, projection_matrix ) hist = integral_image2D( hist ) print hist print "extracting patches..." Y = coordinates[:,0].copy().astype('int32') X = coordinates[:,1].copy().astype('int32') return _patches.extract_oriented_patches2D( img, hist, projection_matrix, X, Y, r )
def test_sg_coeffs_exact(): polyorder = 4 window_length = 9 halflen = window_length // 2 x = np.linspace(0, 21, 43) delta = x[1] - x[0] # The data is a cubic polynomial. We'll use an order 4 # SG filter, so the filtered values should equal the input data # (except within half window_length of the edges). y = 0.5 * x ** 3 - x h = savgol_coeffs(window_length, polyorder) y0 = convolve1d(y, h) assert_allclose(y0[halflen:-halflen], y[halflen:-halflen]) # Check the same input, but use deriv=1. dy is the exact result. dy = 1.5 * x ** 2 - 1 h = savgol_coeffs(window_length, polyorder, deriv=1, delta=delta) y1 = convolve1d(y, h) assert_allclose(y1[halflen:-halflen], dy[halflen:-halflen]) # Check the same input, but use deriv=2. d2y is the exact result. d2y = 3.0 * x h = savgol_coeffs(window_length, polyorder, deriv=2, delta=delta) y2 = convolve1d(y, h) assert_allclose(y2[halflen:-halflen], d2y[halflen:-halflen])
def move_nanmax_filter(arr, window, axis=-1): "Moving window maximium ignoring NaNs, implemented with a filter." global maximum_filter1d, convolve1d if maximum_filter1d is None: try: from scipy.ndimage import maximum_filter1d except ImportError: raise ValueError("'filter' method requires SciPy.") if convolve1d is None: try: from scipy.ndimage import convolve1d except ImportError: raise ValueError("'filter' method requires SciPy.") if axis == None: raise ValueError, "An `axis` value of None is not supported." if window < 1: raise ValueError, "`window` must be at least 1." if window > arr.shape[axis]: raise ValueError, "`window` is too long." arr = arr.astype(float) nrr = np.isnan(arr) arr[nrr] = -np.inf x0 = (window - 1) // 2 maximum_filter1d(arr, window, axis=axis, mode='constant', cval=np.nan, origin=x0, output=arr) w = np.ones(window, dtype=int) nrr = nrr.astype(int) x0 = (1 - window) // 2 convolve1d(nrr, w, axis=axis, mode='constant', cval=0, origin=x0, output=nrr) arr[nrr == window] = np.nan return arr
def test_03_02_adaptive_threshold_different(self): r = np.random.RandomState() r.seed(31) block = r.uniform(size=(10,10)) i,j = np.mgrid[0:10:2,0:10:2] block[i,j] *= .5 i,j = np.mgrid[0:50,0:50] img = block[i%10, j%10] * .5 # # Make the middle higher in intensity # img[20:30, 20:30] *= 2 global_threshold = T.get_global_threshold(T.TM_OTSU, block) adaptive_threshold = T.get_adaptive_threshold( T.TM_OTSU, img, global_threshold, adaptive_window_size = 10) # # Check that the gradients are positive for i,j<15 and negative # for i,j>=15 # gradient = convolve1d(adaptive_threshold, [-1, 0, 1], 0) self.assertTrue(np.all(gradient[20:25, 20:30] < 0)) self.assertTrue(np.all(gradient[25:30, 20:30] > 0)) gradient = convolve1d(adaptive_threshold, [-1, 0, 1], 1) self.assertTrue(np.all(gradient[20:30, 20:25] < 0)) self.assertTrue(np.all(gradient[20:30, 25:30] > 0))
def move_nansum_filter(arr, window, axis=-1): """ Moving sum (ignoring NaNs) along specified axis using the filter method. Parameters ---------- arr : array_like Input array. window : int The number of elements in the moving window. axis : int, optional The axis over which to perform the moving sum. By default the moving sum is taken over the last axis (-1). Returns ------- y : ndarray The moving sum (ignoring NaNs) of the input array along the specified axis.(A window with all NaNs returns NaN for the window sum.) The output has the same shape as the input. Notes ----- The calculation of the sums uses scipy.ndimage.convolve1d. Examples -------- >>> from bottlechest.slow.move import move_sum_filter >>> arr = np.array([1, 2, np.nan, 4, 5, 6, 7]) >>> move_nansum_filter(arr, window=2, axis=0) array([ NaN, 3., 2., 4., 9., 11., 13.]) """ arr = np.array(arr, copy=False) global convolve1d if convolve1d is None: try: from scipy.ndimage import convolve1d except ImportError: raise ValueError("'filter' method requires SciPy.") if axis == None: raise ValueError("An `axis` value of None is not supported.") if window < 1: raise ValueError("`window` must be at least 1.") if window > arr.shape[axis]: raise ValueError("`window` is too long.") arr = arr.astype(float) nrr = np.isnan(arr) arr[nrr] = 0 nrr = nrr.astype(int) w = np.ones(window, dtype=int) x0 = (1 - window) // 2 convolve1d(arr, w, axis=axis, mode='constant', cval=np.nan, origin=x0, output=arr) convolve1d(nrr, w, axis=axis, mode='constant', cval=0, origin=x0, output=nrr) arr[nrr == window] = np.nan return arr
def main(): s = 2.0 m = gauss_1(s) img = imread('cameraman.png') img2 = convolve1d(img, m, axis=0, mode='nearest') img2 = convolve1d(img2, m, axis=1, mode='nearest') imshow(img2, cmap=cm.gray) show()
def simple_gradient(Im): g1=np.array([-0.5, 0, 0.5]) Imx=nd.convolve1d(Im, g1, axis=0) Imy=nd.convolve1d(Im, g1, axis=1) ImMag=(Imx**2 +Imy**2)**0.5 return ImMag, Imx, Imy
def local_standardize(X, kernelsize=(17, 17, 15)): local_sq = X ** 2 local_mean = np.asarray(X) for axis, ks in enumerate(kernelsize): # w = np.ones(ks) / ks w = np.hamming(ks) w /= w.sum() local_sq = convolve1d(local_sq, w, axis=axis, mode="reflect") local_mean = convolve1d(local_mean, w, axis=axis, mode="reflect") return (X - local_mean) / np.sqrt(local_sq - local_mean ** 2)
def GodinTypeFilter(data, n, axis=0): ''' perform 3 times moving average over the specified array axis. suitable for time averaging ''' weights = sp.ones((n),sp.float32)/n weights2 = sp.ones((n+1),sp.float32)/(n+1) data=nd.convolve1d(data, weights, axis=axis, mode='constant') data=nd.convolve1d(data, weights, axis=axis, mode='constant') data=nd.convolve1d(data, weights2, axis=axis, mode='constant') return data
def getSwitchTime(self, pixel=(0,0), useKernel='step', method='convolve1d'): """ getSwitchTime(pixel, useKernel='step', method="convolve1d") Return the position of a step in a sequence and the left and the right values of the gray level (as a tuple) Parameters: --------------- pixel : tuple The (x,y) pixel of the image, as (row, column). useKernel : string step = [1]*5 +[-1]*5 zero = [1]*5 +[0] + [-1]*5 both = step & zero, the one with the highest convolution is chosen method : string For the moment, only the 1D convolution calculation with scipy.ndimage.convolve1d is available """ pxTimeSeq = self.pixelTimeSequence(pixel) if method == "convolve1d": if useKernel == 'step' or useKernel == 'both': convolution_of_stepKernel = nd.convolve1d(pxTimeSeq,self.kernel) minStepKernel = convolution_of_stepKernel.min() switchStepKernel = convolution_of_stepKernel.argmin() +1 switch = switchStepKernel kernel_to_use = 'step' if useKernel == 'zero' or useKernel == 'both': convolution_of_zeroKernel = nd.convolve1d(pxTimeSeq,self.kernel0) minZeroKernel = convolution_of_zeroKernel.min() switchZeroKernel = convolution_of_zeroKernel.argmin() + 1 switch = switchZeroKernel kernel_to_use = 'zero' if useKernel == 'both': if minStepKernel <= minZeroKernel: switch = switchStepKernel kernel_to_use = 'step' else: switch = switchZeroKernel kernel_to_use = 'zero' #leftLevel = np.int(np.mean(pxTimeSeq[0:switch])+0.5) #rightLevel = np.int(np.mean(pxTimeSeq[switch+1:])+0.5) #middle = (leftLevel+rightLevel)/2 #rightLevelStep = np.int(np.mean(pxTimeSeq[switchStepKernel+1:])+0.5) #if abs(pxTimeSeq[switch]-middle)>abs(pxTimeSeq[switch]-rightLevelStep): #switch = switchStepKernel #switch = (switch-1)*(pxTimeSeq[switch]<middle)+switch*(pxTimeSeq[switch]>=middle) #switch = switchStepKernel * (minStepKernel<=minZeroKernel/1.1) + switchZeroKernel * (minStepKernel >minZeroKernel/1.1) else: raise RuntimeError("Method not yet implemented") levels = self._getLevels(pxTimeSeq, switch, kernel_to_use) # Now redefine the switch using the correct image number switch = self.imageNumbers[switch] return switch, levels
def linearconv(C0, wavelet, sliceind, queue, rorc="row"): if rorc == "row": for i in range(C0.shape[0]): C0[i,:] = ndimage.convolve1d(C0[i,:],wavelet) # linearconvker(C0[i,:], wavelet, scale) elif rorc == "column": for i in range(C0.shape[1]): C0[:,i] = ndimage.convolve1d(C0[:,i],wavelet) # linearconvker(C0[:,i], wavelet, scale) queue.put([sliceind,C0])
def move_sum_filter(arr, window, axis=-1): """ Moving window sum along the specified axis using the filter method. Parameters ---------- arr : ndarray Input array. window : int The number of elements in the moving window. axis : int, optional The axis over which to perform the moving sum. By default the moving sum is taken over the last axis (-1). Returns ------- y : ndarray The moving sum of the input array along the specified axis. The output has the same shape as the input. Notes ----- The calculation of the sums uses scipy.ndimage.convolve1d. Examples -------- >>> from bottleneck.slow.move import move_sum_filter >>> arr = np.array([1, 2, 3, 4]) >>> move_sum_filter(arr, window=2, axis=0) array([ NaN, 3., 5., 7.]) """ global convolve1d if convolve1d is None: try: from scipy.ndimage import convolve1d except ImportError: raise ValueError("'filter' method requires SciPy.") if axis == None: raise ValueError, "An `axis` value of None is not supported." if window < 1: raise ValueError, "`window` must be at least 1." if window > arr.shape[axis]: raise ValueError, "`window` is too long." arr = arr.astype(float) w = np.ones(window, dtype=int) x0 = (1 - window) // 2 convolve1d(arr, w, axis=axis, mode='constant', cval=np.nan, origin=x0, output=arr) return arr
def run_gaussian_convolutions(F, s_values): """ This function calculates the Gaussian convolution for a given image F and given values of s in an array and returns an array with the execution times. """ times = np.array([]) for s in s_values: start = datetime.datetime.now() G = convolve1d(F, Gauss1(s), axis=-1, mode='nearest') G = convolve1d(G, Gauss1(s), axis=0, mode='nearest') end = datetime.datetime.now() diff = (end - start).total_seconds() times = np.append(times, diff) return times
def tv_norm(x, beta=2): """Computes the total variation norm and its gradient. From jcjohnson/cnn-vis.""" x_diff = ndimage.convolve1d(x, [-1, 1], axis=2, mode='wrap') y_diff = ndimage.convolve1d(x, [-1, 1], axis=1, mode='wrap') grad_norm2 = x_diff**2 + y_diff**2 + EPS grad_norm_beta = grad_norm2**(beta/2) loss = np.sum(grad_norm_beta) dgrad_norm2 = (beta/2) * grad_norm2**(beta/2 - 1) dx_diff = 2 * x_diff * dgrad_norm2 dy_diff = 2 * y_diff * dgrad_norm2 dxy_diff = dx_diff + dy_diff dx_diff = roll2(dx_diff, (1, 0)) dy_diff = roll2(dy_diff, (0, 1)) grad = dxy_diff - dx_diff - dy_diff return loss, grad
def smooth(self, signal): x = np.asarray(signal) if x.dtype != np.float64 and x.dtype != np.float32: x = x.astype(np.float64) coeffs = self._coeff mode, axis = self.mode, self.axis if mode == "interp": window_length, polyorder = self.n * 2 + 1, self.degree deriv, delta = self.diff_order, self.delta y = convolve1d(x, coeffs, axis=axis, mode="constant") _savitzky_golay._fit_edges_polyfit(x, window_length, polyorder, deriv, delta, axis, y) else: y = convolve1d(x, coeffs, axis=axis, mode=mode, cval=self.cval) return y
def get_model_arc(self): session = object_session(self) daycals = {'B': {}, 'R': {}} daycalfits = session.query(GMOSLongSlitArc).all() daycalfits = [fil for fil in daycalfits if fil.raw.mask.name.startswith('0.5')] for daycal in daycalfits: if daycal.wave_cal is None: if daycal.prepared is None: daycal.raw.prepare_to_database() daycal.longslit_calibrate_to_database() daycals[daycal.raw.instrument_setup.grating.name[:1]][ daycal.raw.instrument_setup.grating_central_wavelength_value ] = daycal.wave_cal.fname instrument_setup = self.science.instrument_setup grating_wavelength = instrument_setup.grating_central_wavelength_value # find corresponding day arc closest = min(daycals[instrument_setup.grating.name[:1]].keys(), key=lambda x: abs(grating_wavelength-x)) dayhdf5 = daycals[instrument_setup.grating.name[:1]][closest] lines = wavecal.read(dayhdf5, path='lines') dayarc = Table.read(dayhdf5, path='arc') filt = np.array([0.15,0.85,0.0,0.06,.88,0.06,0.,0.85,0.15]) fs = convolve1d(dayarc['f'], filt, axis=0, mode='nearest') model_wide_slit_arc = Table([dayarc['w'].flatten(), fs.flatten()], names=['w','f']) model_wide_slit_arc.sort('w') model_wide_slit_arc.meta.update(lines.meta) return model_wide_slit_arc
def findLevelsNd(A, level, mode='rising', axis=0, boxWidth=0): """Function to find level crossings in an Nd numpy array. Can find rising and/or falling crossings, control with the 'mode' paramter. Returns a binary array of level crossings, with true elements right AFTER a crossing. NOTE THAT THIS RETURNS DIFFERENT VALUES THAN findLevels(). if you want to get a list of locations where the crossings occurs, then use the following syntax: levels = findLevelsNd(array, level) level_crossings_locations = levels.nonzero() number_of_level_crossings = len(level_crossing_locations[0]) Often, the crossings are noisy. You can use np.diff() and findLevelsNd() again to help yourself out. :param A: 1d numpy array :param level: floating point to search for in A :param mode: optional string: mode specfication. one of 'rising', 'falling' or 'both' :param axis: optional integer, specifies dimension :param boxWidth: optional int for local boxcar smoothing :returns: binary array of level crossing locations """ assert mode in ('rising', 'falling', 'both'), 'traceManip.findLevels: Unknown mode \'%s\'' % mode if boxWidth is not 0: A = nd.convolve1d(A, np.array([1]*boxWidth)/float(boxWidth), axis=axis) crossings = np.diff(np.sign(A-level), axis=axis) if mode is 'rising': return crossings>0 elif mode is 'falling': return crossings<0 else: return np.abs(crossings>0)
def mtd(t,f,twd): """ Mean Transit Depth Convolve time series with our locally detrended matched filter. Parameters ---------- t : time series f : flux series. f can contain no nans. nans screw up convolution. Interpolate through them. Mask will be copied to dM. twd : Width of kernel in cadances Notes ----- Since a single nan in the convolution kernel will return a nan, we interpolate the entire time series. We see some edge effects """ assert np.where(np.isnan(f))[0].size == 0,\ "f must contain no nans (screws up convolution)" bK,boxK,tK,aK,dK = GenK( twd ) dM = nd.convolve1d(f,dK) dM = ma.masked_array(dM) dM.fill_value=0 return dM
def smooth_responses(rsps, window_width=50, sigma=0.65): # Gaussian smoothing # Values taken from Rajeev's code. sm_rsps = deepcopy(rsps) sm_rsps.data = convolve1d(rsps.data, gaussian(window_width, sigma), axis=2) sm_rsps.data = np.maximum(sm_rsps.data, 0) return sm_rsps
def MF(fsig,twd,fcwd=1): """ Matched filter. """ cwd = fcwd*twd bK,boxK,tK,aK,dK = GenK(twd,fcwd=fcwd) dM = nd.convolve1d(fsig,dK) bM = nd.convolve1d(fsig,bK) aM = nd.convolve1d(fsig,aK) DfDt = (aM-bM)/(cwd+twd)/lc f0 = 0.5 * (aM + bM) # Continuum value of fsig (mid transit) return dM,bM,aM,DfDt,f0
def exp_conv(spike_times, duration, tau, bin_size, causal=True): """ Convolve spike train with an exponential kernel. :param spike_times: List of spike times in seconds. :param tau: Exponential time constant in seconds. :param duration: The duration of the time series. :param bin_size: Bin size in seconds :param causal: Whether to use a causal filter or not. If causal=False, then the spike times are convolved with a two-sided exponential :return: An array time series. """ assert spike_times.min() >= 0, "No negative spike times for exp_conv!" nt = int(duration / bin_size) good_spikes = (spike_times > 0) & (spike_times < duration) i = (spike_times[good_spikes] / bin_size).astype('int') s = np.zeros([nt]) s[i] = 1. # make sure the exponential window size is at least 4 times the time constant winlen = 4*int(tau/bin_size) + 1 assert winlen < len(s), "Signal is too small to convolve with exponential that has tau=%0.3f" % tau hwinlen = int(winlen / 2) twin = np.arange(-hwinlen, hwinlen+1)*bin_size win = np.zeros_like(twin) win[hwinlen:] = np.exp(-twin[hwinlen:] / tau) if ~causal: win[:hwinlen] = win[(hwinlen+1):][::-1] sc = convolve1d(s, win) return sc
def moving_average(data, window_size): # window = [] # means = [] # # if window_size % 2 == 0: # back = int((window_size / 2) - 1) # forward = int(window_size / 2) # else: # back = int((window_size - 1) / 2) # forward = back # # for z in range(back): # window.append(-(z + 1)) # means.append(0) # for z in range(forward + 1): # window.append(z) # # for q in range(back, len(data) - forward): # current = 0 # for i in window: # current += data[q + i] # means.append(current/window_size) # # for z in range(forward): # means.append(0) # Or, do it in two lines. Ya dingus. kernel = (1/window_size)*numpy.ones(window_size) means = convolve1d(data, kernel, mode="nearest") return means
def boxcar(F, dt=0.02, avg_win=1.0): orig_shape = F.shape F = np.atleast_2d(F) npix, nt = F.shape win_len = max(1, avg_win / dt) win = np.ones(win_len) / win_len Fsmooth = ndimage.convolve1d(F, win, axis=1, mode='reflect') return Fsmooth.reshape(orig_shape)
def gD(F, s, iorder, jorder): '''Create the Gaussian derivative convolution of image F.''' functions = [f1, f1_1, f1_2] s = float(s) filt_x = gauss1(s, functions[iorder]) filt_y = gauss1(s, functions[jorder]) gaussFilter = zeros((len(filt_x), len(filt_x))) for x in range(len(filt_x)): for y in range(len(filt_y)): gaussFilter[x][y] = filt_y[y] * filt_x[x] gaussFilter return convolve1d(convolve1d(F, filt_x, axis=0, mode='nearest'), filt_y, axis=1, mode='nearest')
def convolve_rotation(self, vrot, beta=0.4, smallDelta=None, isLog=False, convolveMode='nearest'): """ Convolves the spectrum with a rotational kernel vrot is given in km/s beta is a limb-darkening factor (default=0.4) smallDelta is the wavlength delta that will be used when interpolating isLog - set true if the wavelength solution already has logarithmic spacing convolveMode - mode passed to ndimage.convolve1d """ if not isLog: smallDelta, logSpec = self.interpolate_log(smallDelta) else: smallDelta = self.wave[-1] - self.wave[-2] logSpec = self maxWave = logSpec.wave.max() minWave = logSpec.wave.min() bound = maxWave * (vrot / c) rotKernelX = (np.arange(maxWave - bound, maxWave + bound, smallDelta) - maxWave) / bound rotKernelX[rotKernelX**2 > 1] = 1. rotKernel = ((2 / np.pi) * np.sqrt(1 - rotKernelX**2) + (beta / 2) * (1 - rotKernelX**2)) / (1 + (2 * beta) / 3) rotKernel /= np.sum(rotKernel) rotLogFlux = ndimage.convolve1d(logSpec.flux, rotKernel, mode=convolveMode) rotLogSpec = self.__class__(logSpec.wave, rotLogFlux, mode='waveflux') if isLog: return rotLogSpec else: return rotLogSpec.interpolate(self.wave)
def decompose3d_numpy(arr, level=1, phi=_phi_, boundary1d='mirror', boundary2d='symm'): """Semi-separable a trous wavelet decomposition for 3D data with B3-spline scaling function If `arr` is an input array, then each arr[n] are treated as 2D images and arr[:,j,k] are treated as 1D signals. Parameters: - arr : 3D array - level : level of decomposition - phi : low-pass filter kernel (B3-spline by default) - boundary1d : boundary conditions passed as `mode` to scipy.ndimage.convolve1d - boundary2d : boundary conditions passed to scipy.signal.convolve2d Returns: list of wavelet details + last approximation. Each element in the list is a 3D array of the same size as the input array. """ phi2d = make_phi2d(phi) if level <= 0: return arr arr = arr.astype(_dtype_) tapprox = np.zeros(arr.shape, _dtype_) for loc in locations(arr.shape[1:]): v = arr[:, loc[0], loc[1]] tapprox[:, loc[0], loc[1]] = convolve1d(v, phi, mode=boundary1d) approx = np.zeros(arr.shape, _dtype_) for k in xrange(arr.shape[0]): approx[k] = signal.convolve2d(tapprox[k], phi2d, mode='same', boundary=boundary2d) details = arr - approx upkern = zupsample(phi) shapecheck = map(lambda a, b: a > b, arr.shape, upkern.shape) if level == 1: return [details, approx] elif not np.all(shapecheck): print "Maximum allowed decomposition level reached, returning" return [details, approx] else: return [details] + decompose3d_numpy(approx, level - 1, upkern)
def convolve(signal, sigma, pMin=None, cutoff=None): if cutoff is None: cutoff = KERNEL_CUTOFF kernel = convolution_kernel(sigma, len(signal), pMin) if len(kernel) < cutoff: convSignal = convolve1d(signal, kernel, mode='constant', cval=0.0) else: convSignal = fftconvolve(signal, kernel, mode='full') lenSignal, lenKernel = len(signal), len(kernel) lowerBound = (lenKernel - 1) / 2 convSignal = array( convSignal[lowerBound:lowerBound + lenSignal], copy=True, order='C') # Copy into c-contigous array for c link compatability return convSignal
def __call__(self, spectrum): if np.isclose(self.vrot, 0.0 * u.km / u.s, atol=0.0 * u.km / u.s): return spectrum wavelength, flux = spectrum.wavelength.value, spectrum.flux log_grid_log_wavelength = np.arange(np.log(wavelength.min()), np.log(wavelength.max()), self.resolution.to(1).value) log_grid_wavelength = np.exp(log_grid_log_wavelength) log_grid_flux = np.interp(log_grid_wavelength, wavelength, flux) profile = self.rotational_profile() log_grid_convolved = nd.convolve1d(log_grid_flux, profile) convolved_flux = np.interp(wavelength, log_grid_wavelength, log_grid_convolved) return Spectrum1D.from_array(spectrum.wavelength, convolved_flux, dispersion_unit=spectrum.wavelength.unit, unit=spectrum.unit)
def test_convolution_monte_carlo(input_1, input_2, mode): scipy_modes = valid_modes("scipy") numpy_modes = valid_modes("numpy") # pydynamic calculation y, Uy = convolve_unc(*input_1, *input_2, mode) # Monte Carlo simulation mc_results = [] n_runs = 20000 XX1 = np.random.multivariate_normal(*input_1, size=n_runs) XX2 = np.random.multivariate_normal(*input_2, size=n_runs) for x1, x2 in zip(XX1, XX2): if mode in numpy_modes: conv = np.convolve(x1, x2, mode=mode) elif mode in scipy_modes: conv = sn.convolve1d(x1, x2, mode=mode) mc_results.append(conv) y_mc = np.mean(mc_results, axis=0) Uy_mc = np.cov(mc_results, rowvar=False) # HACK: for visualization during debugging # import matplotlib.pyplot as plt # fig, ax = plt.subplots(nrows=1, ncols=4) # _min = min(Uy.min(), Uy_mc.min()) # _max = max(Uy.max(), Uy_mc.max()) # ax[0].plot(y, label="fir") # ax[0].plot(y_mc, label="mc") # ax[0].set_title("mode: {0}, x1: {1}, x2: {2}".format(mode, len(x1), len(x2))) # ax[0].legend() # ax[1].imshow(Uy, vmin=_min, vmax=_max) # ax[1].set_title("PyDynamic") # ax[2].imshow(Uy_mc, vmin=_min, vmax=_max) # ax[2].set_title("numpy MC") # img = ax[3].imshow(np.log(np.abs(Uy-Uy_mc))) # ax[3].set_title("log(abs(diff))") # fig.colorbar(img, ax=ax[3]) # plt.show() # /HACK assert np.allclose(y, y_mc, rtol=1e-1, atol=1e-1) assert np.allclose(Uy, Uy_mc, rtol=1e-1, atol=1e-1)
def ca_(x, guard_len=4, noise_len=8, mode='wrap', l_bound=4000): """Uses Cell-Averaging CFAR (CA-CFAR) to calculate a threshold that can be used to calculate peaks in a signal. Args: x (~numpy.ndarray): Signal. guard_len (int): Number of samples adjacent to the CUT that are ignored. noise_len (int): Number of samples adjacent to the guard padding that are factored into the calculation. mode (str): Specify how to deal with edge cells. Examples include 'wrap' and 'constant'. l_bound (float or int): Additive lower bound while calculating peak threshold. Returns: Tuple [ndarray, ndarray] 1. (ndarray): Upper bound of noise threshold. #. (ndarray): Raw noise strength. Examples: >>> signal = np.random.randint(100, size=10) >>> signal array([41, 76, 95, 28, 25, 53, 10, 93, 54, 85]) >>> threshold = mm.dsp.ca_(signal, l_bound=20, guard_len=1, noise_len=3) >>> threshold (array([70, 76, 64, 79, 81, 91, 74, 71, 70, 79]), array([50, 56, 44, 59, 61, 71, 54, 51, 50, 59])) Perform a non-wrapping CFAR thresholding >>> signal = np.random.randint(100, size=10) >>> signal array([41, 76, 95, 28, 25, 53, 10, 93, 54, 85]) >>> threshold = mm.dsp.ca_(signal, l_bound=20, guard_len=1, noise_len=3, mode='constant') >>> threshold (array([44, 37, 41, 65, 81, 91, 67, 51, 34, 46]), array([24, 17, 21, 45, 61, 71, 47, 31, 14, 26])) """ if isinstance(x, list): x = np.array(x) assert type(x) == np.ndarray kernel = np.ones(1 + (2 * guard_len) + (2 * noise_len), dtype=x.dtype) / (2 * noise_len) kernel[noise_len:noise_len + (2 * guard_len) + 1] = 0 noise_floor = convolve1d(x, kernel, mode=mode) threshold = noise_floor + l_bound return threshold, noise_floor
def ca_(arr, l_bound=4000, guard_len=4, noise_len=8): """Perform CFAR-CA detection on the input array. Args: arr (list or ndarray): Noisy array. l_bound (int): Additive lower bound of detection threshold. guard_len (int): Left and right side guard samples for leakage protection. noise_len (int): Left and right side noise samples after guard samples. Returns: threshold (ndarray): CFAR generated threshold based on inputs (Peak detected if arr[i] > threshold[i]) \ for designated false-positive rate noise_floor (ndarray): noise values with the same shape as input arr. Example: >>> signal = np.random.randint(100, size=10) >>> signal array([41, 76, 95, 28, 25, 53, 10, 93, 54, 85]) >>> threshold = mm.dsp.ca_(signal, l_bound=20, guard_len=1, noise_len=3) >>> threshold (array([70, 76, 64, 79, 81, 91, 74, 71, 70, 79]), array([50, 56, 44, 59, 61, 71, 54, 51, 50, 59])) FEATURE NOT YET ADDED - Perform a non-wrapping cfar thresholding. >>> signal = np.random.randint(100, size=10) >>> signal array([41, 76, 95, 28, 25, 53, 10, 93, 54, 85]) >>> threshold = mm.dsp.ca_(signal, l_bound=20, guard_len=1, noise_len=3, wrap=False) >>> threshold (array([70, 76, 64, 79, 81, 91, 74, 71, 70, 79]), array([50, 56, 44, 59, 61, 71, 54, 51, 50, 59])) """ if isinstance(arr, list): arr = np.array(arr) assert type(arr) == np.ndarray kernel = np.ones(1 + (2 * guard_len) + (2 * noise_len), dtype=arr.dtype) / (2 * noise_len) kernel[noise_len:noise_len + (2 * guard_len) + 1] = 0 noise_floor = convolve1d(arr, kernel, mode='wrap') threshold = noise_floor + l_bound return threshold, noise_floor
def compute_energy_freq_bands(sfreq, data, freq_bands=np.array( [0.5, 4., 8., 13., 30., 100.]), deriv_filt=True): """ Energy (of the signal, filtered by frequency bands ; per channel) [1]. Parameters ---------- sfreq : float Sampling rate of the data. data : ndarray, shape (n_channels, n_times) freq_bands : ndarray, shape (n_freqs,) (default: np.array([0.5, 4., 8., 13., 30., 100.])) Array defining the frequency bands. The j-th frequency band is defined as: [freq_bands[j], freq_bands[j + 1]] (0 <= j <= n_freqs - 1). deriv_filt : bool (default: False) If True, a derivative filter is applied to the input data before filtering (see Notes). Returns ------- output : ndarray, shape (n_channels * (n_freqs - 1),) References ---------- .. [1] Kharbouch, A. et al. (2011). An algorithm for seizure onset detection using intracranial EEG. Epilepsy & Behavior, 22, S29-S35. """ n_freqs = freq_bands.shape[0] n_channels = data.shape[0] band_energy = np.empty((n_channels, n_freqs - 1)) if deriv_filt: _data = convolve1d(data, [1., 0., -1.], axis=-1, mode='nearest') else: _data = data for j in range(1, n_freqs): filtered_data = filt(sfreq, _data, freq_bands[(j - 1):(j + 1)]) band_energy[:, j - 1] = np.sum(filtered_data**2, axis=-1) return band_energy.ravel()
def test_filter_waveforms(): """Test that filter_records gives the same output as a simple convolution applied to the original pulse (before splitting into records) """ wv = np.random.randn(300) ir = np.random.randn(41) ir[10] += 10 # Because it crashes for max at edges origin = np.argmax(ir) - (len(ir) // 2) wv_after = convolve1d(wv, ir, mode='constant', origin=origin) wvs = wv.reshape(3, 100) wvs = strax.filter_waveforms(wvs, ir, prev_r=np.array([strax.NO_RECORD_LINK, 0, 1]), next_r=np.array([1, 2, strax.NO_RECORD_LINK])) wv_after_2 = np.reshape(wvs, -1) assert np.abs(wv_after - wv_after_2).sum() < 1e-9
def low_pass(x, T, cutoff, axis=-1): ''' :param x: The signal to be filtered (1D or 2D) :param T: Sampling rate of the signal, x :param cutoff: Cutoff frequency in Hertz ''' # Construct the filter Fs = 1. / T ntaps = np.ceil(Fs / cutoff) + 10 # Make sure its odd ntaps += 1 - (ntaps % 2) # window = ('kaiser', 1) # window = ('chebwin', 120) # window = ('gaussian', ntaps//3) # window = 'nuttall' window = 'hamming' # window = 'boxcar' b = signal.firwin(ntaps, cutoff, window=window, nyq=0.5 * Fs) return ndimage.convolve1d(x, b, axis=axis)
def run(self): """ Used to run MOOG silent. """ self.create_batch() # Running MOOGSILENT os.system('MOOGSILENT > moog.log 2>&1') os.remove('batch.par') # Grabing the synthetic and observed spectrum synth_wl = np.loadtxt('vm_smooth.out', skiprows=2, usecols=(0, )) synth_flux = np.loadtxt('vm_smooth.out', skiprows=2, usecols=(1, )) if self.vsini > 0.0: # Applying smart_cut() before rotational convolution synth_wl, synth_flux, self.obs_wl, self.obs_flux = \ self.smart_cut(synth_wl, synth_flux, self.obs_wl, self.obs_flux) # Finding the line info corresponding to the wavelength in question lines = np.loadtxt('lines.dat', usecols=(0, ), skiprows=1) wl_0 = lines[np.where( np.abs(lines - self.syn_start) == np.min( np.abs(lines - self.syn_start)))[0][0]] # Wavelength to velocity space c = 2.998E5 # km/s synth_v = c * (synth_wl - wl_0) / wl_0 # The rotational profile vsini_profile = self.rot_prof(synth_v) # Convolving the non-rotating spectrum with the rotational profile conv_flux = convolve1d(synth_flux, vsini_profile) with open('vm_smooth.out', 'w') as f: f.write('Smoothed spectrum\n') f.write('Do not mind this useless line\n') for i in range(len(conv_flux)): f.write(' %.3f %.5f\n' % (synth_wl[i], conv_flux[i] / max(conv_flux))) # Plotting/saving a plot self.plot(synth_wl, synth_flux)
def _rolling_mean_detrending(self, trace, frame_times, cropping_offset=10, window_size=300): cropped_start_mask = frame_times > (cropping_offset + np.nanmin(frame_times)) cropped_end_mask = frame_times < (np.nanmax(frame_times) - cropping_offset) cropping_mask = np.all((cropped_start_mask, cropped_end_mask), axis=0) trace_fps = 1 / np.median(np.diff(frame_times)) rolling_mean_size = int(trace_fps * window_size) rolling_mean = convolve1d(trace[cropping_mask], np.ones(rolling_mean_size) / rolling_mean_size, mode="reflect") return_trace = trace.copy() return_trace[cropping_mask] -= rolling_mean return return_trace
def _get_bucket_weights(self, args): assert args.reweight in {'none', 'inverse', 'sqrt_inv'} assert args.reweight != 'none' if args.lds else True, "Set reweight to \'sqrt_inv\' or \'inverse\' (default) when using LDS" if args.reweight == 'none': return None logging.info(f"Using re-weighting: [{args.reweight.upper()}]") if args.lds: value_lst = TRAIN_BUCKET_NUM[args.bucket_start:] lds_kernel_window = get_lds_kernel_window(args.lds_kernel, args.lds_ks, args.lds_sigma) logging.info( f'Using LDS: [{args.lds_kernel.upper()}] ({args.lds_ks}/{args.lds_sigma})' ) if args.reweight == 'sqrt_inv': value_lst = np.sqrt(value_lst) smoothed_value = convolve1d(np.asarray(value_lst), weights=lds_kernel_window, mode='reflect') smoothed_value = [smoothed_value[0] ] * args.bucket_start + list(smoothed_value) scaling = np.sum(TRAIN_BUCKET_NUM) / np.sum( np.array(TRAIN_BUCKET_NUM) / np.array(smoothed_value)) bucket_weights = [ np.float32(scaling / smoothed_value[bucket]) for bucket in range(args.bucket_num) ] else: value_lst = [ TRAIN_BUCKET_NUM[args.bucket_start] ] * args.bucket_start + TRAIN_BUCKET_NUM[args.bucket_start:] if args.reweight == 'sqrt_inv': value_lst = np.sqrt(value_lst) scaling = np.sum(TRAIN_BUCKET_NUM) / np.sum( np.array(TRAIN_BUCKET_NUM) / np.array(value_lst)) bucket_weights = [ np.float32(scaling / value_lst[bucket]) for bucket in range(args.bucket_num) ] return bucket_weights
def pointils2(band,wave): #VERSION 2 updates for replanned optics (smaller grating footprint) gratingsizes = np.array([81., 81., 84.4, 84.4]) #make function to generate pointils. #convolution of grating function with airy function for the relevant band deltawave = 1e-6 [sigma,alpha,beta0,order,fcam] = get_geocarb_gratinginfo(band) gratingsize=gratingsizes[band] #find central wavelength cenwave = 0.5*(wave[len(wave)//2]+wave[len(wave)//2+1])#gratinglambda(sigma,alpha,beta0,m=order) #wave=np.arange(0.001*2/deltawave)*deltawave+cenwave-0.001 #compute beta angles for these wavelengths betas = betaangle(wave,sigma,alpha,m=order) #FIRST DO GRATING FUNCTION #number of illuminated grooves Ngrooves = gratingsize*1000./sigma #phase shift deltaphi = 2*np.pi*sigma/cenwave*(np.sin(betas*dtor)-np.sin(beta0*dtor)) #total phase shift across grating phi = Ngrooves*deltaphi inten = 1/Ngrooves**2*(np.sin(phi/2)/np.sin(deltaphi/2))**2 deltawave = wave-cenwave #NOW FOR AIRY FUNCTION k = 2*np.pi/cenwave ap = 75./2./2. #radius of aperture in mm (extra factor of two from descope) bx = k*ap*1000.*np.sin((betas-beta0)*dtor) #take into account that beam speed in spectral direction #has changed due to grating magnification bx = bx*np.cos(beta0*dtor)/np.cos(alpha*dtor) airy = (2*besselj(1,bx)/bx)**2 #pdb.set_trace() airy = airy/np.nanmax(airy) #diffraction limit FWHM diffFWHM = cenwave*3.2*np.sqrt(2)*np.cos(alpha*dtor)/np.cos(beta0*dtor) #POINT ILS IS CONVOLUTION OF GRATING FUNCTION WITH AIRY FUNCTION pointils = convolve1d(inten,airy, mode='constant', cval=0.0) #pdb.set_trace() pointils = pointils/pointils.max() return pointils
def get_stim_response_separable(center_surround_filter, t_filter, stimulus): '''Compute stimulus response from a single cell separable STRF.''' # from scipy.signal import convolve as convolve from scipy.ndimage import convolve1d # First reduce the size of the matrix by multiplying by space filter. # The filter hex array can be first mutiplied then summed or vice versa? # This is important for the function calling this function. # s_filter = center_surround_filter / np.sum(center_surround_filter**2) # s_filter = center_surround_filter / np.sum(np.abs(center_surround_filter)) # s_filter = center_surround_filter / np.linalg.norm(center_surround_filter, ord=1) s_filter = center_surround_filter / np.sum(center_surround_filter) response = np.zeros(stimulus.shape[-1]) for t in np.arange(0, stimulus.shape[-1]): response[t] = np.sum(np.multiply(stimulus[:, :, t], s_filter)) # Adding origin, corrects for the shift in timing induced by convolution, # which makes the neuron respond before the stimulus onset. response = convolve1d(response, np.flipud(t_filter), mode='constant', cval=0, origin=-int(t_filter.shape[-1] // 2)) return response
def fast_snip1d(y, w=4, numiter=2, mask=None): """ Return SNIP-estimated baseline-background for given spectrum y. FIXME: behavior of mask kwarg is not finalized """ if mask is not None: for ir, rmask in enumerate(mask): if np.sum(~rmask) > 0: y[ir, rmask] = np.median(y[ir, ~rmask]) z = np.log(np.log(np.sqrt(y + 1) + 1) + 1) b = z for i in range(numiter): for p in range(w, 0, -1): kernel = np.zeros(p * 2 + 1) kernel[0] = kernel[-1] = 1. / 2. b = np.minimum(b, ndimage.convolve1d(z, kernel, mode='reflect')) z = b bkg = (np.exp(np.exp(b) - 1) - 1)**2 - 1 return bkg
def forward(arr, ax): """forward difference .. math:: d_n = x_{n+1} - x{n} Parameters ---------- arr: array_like ax: integer along which axes to compute the difference Returns ------- array_like forward difference """ return convolve1d(arr, np.array([1, -1]), axis=ax)
def gaussian_baseline(image, sigma, window_size, axes=2, skip_axes=0, dtype=np.uint8): sigma_xyz = to_cv_sigma(sigma, axes) win_xyz = to_cv_win_size(window_size, axes, sigma) filters = [ cv2.getGaussianKernel(win_xyz[i], sigma_xyz[i]) for i in range(axes) ] filters = [np.float32(f).squeeze() for f in filters] filters.reverse() for i in reversed(range(axes)): axis = i + skip_axes image = convolve1d(np.float32(image), filters[i], axis, mode="mirror") if dtype == np.float32: return image else: return dtype(image + 0.5)
def backward(arr, ax): """backward difference .. math:: d_n = x_{n} - x{n-1} Parameters ---------- arr: array_like ax: integer along which axes to compute the difference Returns ------- array_like backward difference """ return convolve1d(arr, np.array([1, -1]), axis=ax, origin=-1)
def resample_to_timepoints(timepoints: np.ndarray, data: np.ndarray, ref_timepoints: DataChunk, group="data") -> DataChunk: """ Resample the data at timepoints to new timepoints given by ref_timepoints. Return a DataChunk of the resampled data belonging to a specified group. params: - timepoints: Original timepoints of the data - data: Data to resample of shape (t, ...) - ref_timepoints: Target timepoints for the resampling - group: Group assigned to the returned DataChunk return: - Resampled datachunk with appropriate idx. """ assert len(timepoints) == len(data) timepoints = np.array(timepoints) data = np.array(data) start_idx = np.argmax(ref_timepoints >= timepoints[0]) stop_idx = np.argmax(ref_timepoints >= timepoints[-1]) if stop_idx == 0: stop_idx = len(ref_timepoints) if len(ref_timepoints[start_idx:stop_idx]) < len( timepoints): #Downsampling distance = (np.argmax(timepoints > ref_timepoints[start_idx + 1]) - np.argmax(timepoints > ref_timepoints[start_idx])) kernel = np.ones(distance) / distance data = convolve1d(data, kernel, axis=0) #Smooting to avoid weird sampling new_data = interpolate.interp1d(timepoints, data, axis=0)(ref_timepoints[start_idx:stop_idx]) idx = ref_timepoints.idx + start_idx return DataChunk(data=new_data, idx=idx, group=group)
def get_waveform(self, charge, time, n_samples): """Obtain the waveform toy model. Parameters ---------- charge : ndarray Amount of charge in each pixel Shape: (n_pixels) time : ndarray The signal time in the waveform in nanoseconds Shape: (n_pixels) n_samples : int Number of samples in the waveform Returns ------- waveform : ndarray Toy model waveform Shape (n_pixels, n_samples) """ n_pixels = charge.size n_upsampled_samples = n_samples * self.upsampling readout = np.zeros((n_pixels, n_upsampled_samples)) sample = (time / self.ref_width_ns).astype(np.int64) outofrange = (sample < 0) | (sample >= n_upsampled_samples) sample[outofrange] = 0 charge[outofrange] = 0 readout[np.arange(n_pixels), sample] = charge convolved = convolve1d(readout, self.ref_interp_y, mode="constant", origin=self.origin) sampled = ( convolved.reshape( (n_pixels, convolved.shape[-1] // self.upsampling, self.upsampling)).sum(-1) * self.ref_width_ns # Waveform units: p.e. ) return sampled
def findLevelsNd(A, level, mode='rising', axis=0, boxWidth=0): """Function to find level crossings in an Nd numpy array. Can find rising and/or falling crossings, control with the 'mode' paramter. Returns a binary array of level crossings, with true elements right AFTER a crossing. NOTE THAT THIS RETURNS DIFFERENT VALUES THAN findLevels(). if you want to get a list of locations where the crossings occurs, then use the following syntax: levels = findLevelsNd(array, level) level_crossings_locations = levels.nonzero() number_of_level_crossings = len(level_crossing_locations[0]) Often, the crossings are noisy. You can use np.diff() and findLevelsNd() again to help yourself out. :param A: 1d numpy array :param level: floating point to search for in A :param mode: optional string: mode specfication. one of 'rising', 'falling' or 'both' :param axis: optional integer, specifies dimension :param boxWidth: optional int for local boxcar smoothing :returns: binary array of level crossing locations """ assert mode in ( 'rising', 'falling', 'both'), 'traceManip.findLevels: Unknown mode \'%s\'' % mode if boxWidth is not 0: A = nd.convolve1d(A, np.array([1] * boxWidth) / float(boxWidth), axis=axis) crossings = np.diff(np.sign(A - level), axis=axis) if mode is 'rising': return crossings > 0 elif mode is 'falling': return crossings < 0 else: return np.abs(crossings > 0)
def smooth1d(array, window_size=None, kernel='gaussian'): """Apply a centered window smoothing to a 1D array. Parameters ---------- array : ndarray the array to apply the smoothing to window_size : int the size of the smoothing window kernel : str the type of smoothing (`gaussian`, `mean`) Returns ------- the smoothed array (same dim as input) """ # some defaults if window_size is None: if len(array) >= 9: window_size = 9 elif len(array) >= 7: window_size = 7 elif len(array) >= 5: window_size = 5 elif len(array) >= 3: window_size = 3 if window_size % 2 == 0: raise ValueError('Window should be an odd number.') if isinstance(kernel, str): if kernel == 'gaussian': kernel = gaussian(window_size, 1) elif kernel == 'mean': kernel = np.ones(window_size) else: raise NotImplementedError('Kernel: ' + kernel) kernel = kernel / np.asarray(kernel).sum() return convolve1d(array, kernel, mode='mirror')
def generate(self, min_x, max_x): res = float(self.parent.resolution.get()) epsilon = float(self.parent._epsilon.get()) mf = float(self.parent.machine_frequency_mhz.get()) xs, ys = self.cauchy(min_x, max_x) if len(xs) == 0: return [], [] for S in self.splittings: nuclei = int(S.nuclei.get()) spin = float(S.spin.get()) coupling = float(S.coupling.get()) s = list(S.get_splitting()) j_split = float(coupling) / mf max_j = (nuclei * spin) * j_split conv_xs = np.arange(-max_j, max_j + res, res) conv_ys = [] j = -max_j for i, conv_x in enumerate(conv_xs): if j - conv_x <= epsilon: conv_ys.append(s.pop(0)) j += j_split * 0.5 else: conv_ys.append(0.0) ys = ndi.convolve1d(ys, conv_ys) return xs, np.array(ys)
def test_convolve1d(dtype_x, dtype_h, len_x, mode): x_cpu = np.arange(1, 1 + len_x, dtype=dtype_x) for len_h in range(1, len_x): h_cpu = np.arange(1, 1 + len_h, dtype=dtype_h) min_origin = -(len_h // 2) max_origin = (len_h - 1) // 2 for origin in range(min_origin, max_origin + 1): y = ndi.convolve1d(x_cpu, h_cpu, mode=mode, cval=0, origin=origin) # test via convolve1d y3 = convolve1d( cp.asarray(x_cpu), cp.asarray(h_cpu), mode=mode, cval=0, origin=origin, ) cp.testing.assert_allclose(y, y3) # test using upfirdn directly offset = len(h_cpu) // 2 + origin mode_kwargs = _get_ndimage_mode_kwargs(mode, cval=0) y2 = upfirdn( cp.asarray(h_cpu), cp.asarray(x_cpu), offset=offset, **mode_kwargs, )[:len_x] cp.testing.assert_allclose(y, y2) for origin in [min_origin - 1, max_origin + 1]: with pytest.raises(ValueError): convolve1d( cp.asarray(x_cpu), cp.asarray(h_cpu), mode=mode, cval=0, origin=origin, )
def Hessian2D_separable(I,Sigma=1.0): # Make kernel coordinates s = round(3*Sigma) x=np.mgrid[-s:s+1] Gauss = np.exp(-(x**2)/(2*Sigma**2)) * 1/(np.sqrt(2*np.pi)*Sigma) DGxx1D = -(Sigma**2 - x**2) * np.exp(-(x**2)/(2*Sigma**2)) * 1/(np.sqrt(2*np.pi)*Sigma**5) DGx1D = - x * np.exp(-x**2/(2*Sigma**2)) * 1/(np.sqrt(2*np.pi)*Sigma**3) Dx1 = ndimage.convolve1d(I,DGxx1D,axis=0) Dxx = ndimage.convolve1d(Dx1,Gauss,axis=1) Dy1 = ndimage.convolve1d(I,DGxx1D,axis=1) Dyy = ndimage.convolve1d(Dy1,Gauss,axis=0) Dx = ndimage.convolve1d(I, DGx1D,axis=0) Dxy = ndimage.convolve1d(Dx,DGx1D,axis=1) return [Dxx,Dxy,Dyy]
def calculate_trajectory(ax, spacing=0.5, axis=0, correlation_distance='auto'): """ Calculate trajectory using acceleration data. :param ax: acceleration data :param spacing: distance between two samples :param axis: if ``x`` is multidimensional array, then trajectory will be calculated along specified axis :param correlation_distance: approximage correlation distance between samples (it's used to suppress low frequency noises) :return: restored trajectory """ if correlation_distance == 'auto': correlation_distance = 1 / (spacing * 0.05) if correlation_distance is not None: if correlation_distance < 0: raise ValueError("Correlation should be positive") correlation_distance_n_samples = int(correlation_distance * (0.5 / spacing)) b = [spacing] exp_mean_k = 2 / (1 + correlation_distance_n_samples) a = [1, -1 + exp_mean_k] vx = signal.lfilter(b=b, a=a, x=ax) x = signal.lfilter(b=b, a=a, x=vx) low_pass_fir_b = signal.get_window('hamming', correlation_distance_n_samples) low_pass_fir_b /= low_pass_fir_b.sum() x -= ndimage.convolve1d(x, low_pass_fir_b, axis=axis, mode='mirror') else: vx = cumtrapz(ax, dx=spacing, axis=axis, initial=0) x = cumtrapz(vx, dx=spacing, axis=axis, initial=0) return x
def get_germes_histo(img, nb_points): gray = cv.cvtColor(img, cv.COLOR_BGR2GRAY) histr = cv.calcHist([gray], [0], None, [256], [0, 256]) plt.imshow(gray, cmap='gray') plt.show() plt.plot(histr) plt.show() k = 15 d = k // 2 # z = bn.partition(-ravel, nb_points)[:nb_points] starting_points = [] histr = convolve1d(histr, np.ones(k)) histr[:10] = 0 histr[250:] = 0 for i in range(nb_points): print("------") imax = np.argmax(histr) print(imax) a = max(imax - 1, 0) b = min(imax + 1, 255) print((a, b)) # histr[a:b] = np.log(histr[a:b]) histr[a:b] /= 2 print("[a:b]: ", histr[a:b]) (cx, cy) = np.where(gray == imax) starting_points.append((cx[0], cy[0])) return starting_points
def savitzky_golay_filter(data, window, polyorder, pos_back=1, deriv=0, axis=-1, mode='nearest'): """ Výpočet Savitzky-Golay filtru - aproximace klouzavého okna (hodnoty uvnitř) pomocí konvoluce s polynomeme Input: data .. vektor dat (np.array() "1D") window .. časový úsek, na kterém je počítán SG filtr " (int) polyorder .. řád polynomu, který je využit při vyhlazování dat v okně (int) pos_back .. je pozice od konce okna, ve níž probíhá aproximace, posunem pozice ze středu okna přicházíme o robustnost (int) Output: output .. data vyhlazená pomocí S-G filtru (np.array() "1D") """ if pos_back > window: raise ValueError("pozice není uvnitř okna") #okraje mám defaulte pomocí nearest => nakopíruje krajní body if mode not in ["mirror", "nearest", "wrap"]: raise ValueError("mode must be 'mirror', 'nearest' or 'wrap'") data = np.asarray(data) # Nastavli jsem, aby se koeficienty počítaly v posledním bodě -> pos = window_lenght-1 coeffs = savgol_coeffs(window, polyorder, pos=window - pos_back, deriv=deriv) # dále používám stejnou konvoluci jako je v originále output = convolve1d(data, coeffs, axis=axis, mode=mode, cval=0.0) return output
def wavelet_backTransform(coefficients): """Transform from wavelet to real space.""" # We have array number = levels + 1 (due to the smoothing coefficients) coefficients = np.array(coefficients, dtype=float) levels = coefficients.shape[0] - 1 h_coefficients = get_h_coefficients(levels) # We convolve each wavelet and the smoothing function with the # corresponding h array to re-transform into image space. # We have to go in reverse order. # Initialize the coefficients for the convolution signal = coefficients[levels] for i in range(levels): # levels-1 because python begins counting at 0 signal_convolved = convolve1d(signal, h_coefficients[levels - 1 - i], mode='wrap') # We add the corresponding coefficients for the next convolution signal = signal_convolved + coefficients[levels - 1 - i] return signal