Ejemplo n.º 1
0
    def find_w1_peaks(self, flag_verbose = False):

        data = self.mess.s[self.w1_peaks_y_i[0]:self.w1_peaks_y_i[1], self.w1_peaks_x_i[0]:self.w1_peaks_x_i[1]]
        y_axis = self.mess.s_axis[0][self.w1_peaks_y_i[0]:self.w1_peaks_y_i[1]]        

        y = numpy.sum(data,1)

        A_out = MATH.fit(y_axis, y, EQ.rb_lorentzian, self.w1_peaks_A_in)

        self.w1_peaks[0] = A_out[1]
Ejemplo n.º 2
0
    def fit_double_lorentzian(self, flag_plot = False, flag_verbose = False):
        """
        For a selection of points on the w1-axis, take a cut (giving w3 vs z (intensity) plot) and fit it with a double Lorentzian. 
        self.dl_x_i[0] etc are the min/max indices to be fitted
        """

        if flag_verbose:
            self.verbose("Fit double Lorentzian for " + self.objectname, flag_verbose = flag_verbose)
            self.verbose("  x_min: " + str(self.dl_x_i[0]) + " " + str(self.mess.s_axis[2][self.dl_x_i[0]]), flag_verbose = flag_verbose)
            self.verbose("  x_max: " + str(self.dl_x_i[1]) + " " + str(self.mess.s_axis[2][self.dl_x_i[1]]), flag_verbose = flag_verbose)
            self.verbose("  y_min: " + str(self.dl_y_i[0]) + " " + str(self.mess.s_axis[0][self.dl_y_i[0]]), flag_verbose = flag_verbose)
            self.verbose("  y_max: " + str(self.dl_y_i[1]) + " " + str(self.mess.s_axis[0][self.dl_y_i[1]]), flag_verbose = flag_verbose)

        # select the part of the data to be fitted
        data = self.mess.s[self.dl_y_i[0]:self.dl_y_i[1], self.dl_x_i[0]:self.dl_x_i[1]]
        x_axis = self.mess.s_axis[2][self.dl_x_i[0]:self.dl_x_i[1]]
        y_axis = self.mess.s_axis[0][self.dl_y_i[0]:self.dl_y_i[1]]
        
        # arrays for the results
        n_y, n_x = numpy.shape(data)
        y_max = numpy.zeros(n_y)                # index of the maximum
        y_min = numpy.zeros(n_y)                # index of the minimum
        y_out_array = numpy.zeros((n_y, 8))     # fitting parameters

        if flag_plot:
            plt.figure()
            color_array = ["b", "g", "r", "c", "m", "y", "k"]

        # calculate the fit for the cut of w1
        for i in range(n_y):

            y = data[i,:]

            A_out = MATH.fit(x_axis, y, EQ.rb_two_lorentzians, self.dl_A_in)        

            y_out_array[i,:] = A_out

            x_fit = numpy.arange(x_axis[0], x_axis[-1], 0.1)
            y_fit = EQ.rb_two_lorentzians(A_out, x_fit)

            if flag_plot:  
                plt.plot(x_fit, y_fit, c = color_array[i%len(color_array)])
                plt.plot(x_axis, y, ":", c = color_array[i%len(color_array)])

            y_max[i] = x_fit[numpy.argmax(y_fit)]
            y_min[i] = x_fit[numpy.argmin(y_fit)]

        self.dl_ble = y_min
        self.dl_esa = y_max
        self.dl_A = y_out_array

        if flag_plot:
            plt.show()
Ejemplo n.º 3
0
    def fit_tilt(self, flag_verbose = False):

        if flag_verbose:
            self.verbose("Fit tilt for " + self.objectname, flag_verbose = flag_verbose)
            self.verbose("  x_min: " + str(self.dl_x_i[0]) + " " +  str(self.mess.s_axis[2][self.dl_x_i[0]]), flag_verbose = flag_verbose)
            self.verbose("  x_max: " + str(self.dl_x_i[1]) + " " +  str(self.mess.s_axis[2][self.dl_x_i[1]]), flag_verbose = flag_verbose)
            self.verbose("  y_min: " + str(self.dl_y_i[0] + self.l_i[0]) + " " +  str(self.mess.s_axis[0][self.dl_y_i[0] + self.l_i[0]]), flag_verbose = flag_verbose)
            self.verbose("  y_max: " + str(self.dl_y_i[0] + self.l_i[1]) + " " +  str(self.mess.s_axis[0][self.dl_y_i[0] + self.l_i[1]]), flag_verbose = flag_verbose)

        y = self.mess.s_axis[0][self.dl_y_i[0] + self.l_i[0]:self.dl_y_i[0] + self.l_i[1]]     

        x = self.dl_ble[self.l_i[0]:self.l_i[1]]
        self.l_A_ble = MATH.fit(x, y, EQ.linear, self.l_A_in)

        x = self.dl_esa[self.l_i[0]:self.l_i[1]]
        self.l_A_esa = MATH.fit(x, y, EQ.linear, self.l_A_in)

        self.l_angle_ble = 90 - numpy.arctan(self.l_A_ble[1]) * 180 / numpy.pi
        self.l_angle_esa = 90 - numpy.arctan(self.l_A_esa[1]) * 180 / numpy.pi

        self.l_slope_ble = 1 / self.l_A_ble[1]
        self.l_slope_esa = 1 / self.l_A_esa[1]
Ejemplo n.º 4
0
    def make_plot(self, ax = False, normalize = False, fit = False):
        """
        Make a plot of scan spectrum data. 
    
        INPUT:
        - ax (plt axis instance, or False): If False, a new figure and axis instance will be made. 
        - normalize (bool, False): If True, the minimum is subtract from the data, then it is divided by the maximum. 
        - fit (Bool, False): If True, a fit will be made and will also be plotted. The fitting parameters are written to the terminal. 
    
        CHANGELOG:
        201604-RB: started function
    
        """
        if ax == False:
            fig = plt.figure()
            ax = fig.add_subplot(111)
        
        if normalize:
            for ds in range(self.r_n[2]):
                self.r[:,0,ds,0,0,0,0,0] -= numpy.nanmin(self.r[:,0,ds,0,0,0,0,0])
                self.r[:,0,ds,0,0,0,0,0] /= numpy.nanmax(self.r[:,0,ds,0,0,0,0,0])

        ax.plot(self.r_axes[0], self.r[:,0,0,0,0,0,0,0], color = "g")
        ax.plot(self.r_axes[0], self.r[:,0,1,0,0,0,0,0], color = "r")
             
             
        
        if fit:
            colors = ["lightgreen", "orange"]
            labels = ["probe", "reference"]
            sigma = (self.r_axes[0][0] - self.r_axes[0][-1]) / 4

                      
            print("           mu       sigma   offset    scale")
            for ds in range(self.r_n[2]):
                A = [sigma, self.r_axes[0][numpy.argmax(self.r[:,0,ds,0,0,0,0,0])], 0, 1] # initial guess
            
                A_final = M.fit(self.r_axes[0], self.r[:,0,ds,0,0,0,0,0], EQ.rb_gaussian, A)
                ax.plot(self.r_axes[0], EQ.rb_gaussian(A_final, self.r_axes[0]), color = colors[ds])
                
                print("{label:10} {mu:.5}   {sigma:.3}   {offset:.3}   {scale:.3}".format(label = labels[ds], mu = A_final[1], sigma = A_final[0], offset = A_final[2], scale = A_final[3]))
Ejemplo n.º 5
0
def calculate_pulse_length(data, A = [], dt = CONST.hene_fringe_fs, plot_results = True, print_results = True, fwhm_limit = 200, mu_shift = 10, flag_recursive_limit = False):

    """
    Calculate the pulse length
    
    INPUT:
    data (array): the result of a measure phase measurement for one pulse pair. Usually measure phase is saved as two measurements of two pulse pairs. 
    A (list, default = []): [sigma, mu, offset, scale, frequency, phase] if A is empty, some reasonable default values are used.
    dt (float, HeNe-fringe in fs): to convert from indices to time
    plot (BOOL, True): plot the results
    print_res (BOOL, True): print the results
    fwhm_limit (float, 200): if FWHM is above this limit, it will try again by shifting the mean a bit (by mu_shift)
    mu_shift (float, 10): shift the mean a bit
    flag_recursive_limit (BOOL, False): function will try again if set to False. To prevent endless recursion.
    
    OUTPUT:
    - the output can be plotted to confirm the fit
    - the fitting results can be printed
    - the FWHM is returned
    
    CHANGELOG:
    20130408/RB: started function
    """

    # input for a single IR pulse    
    if A == []:
        A = default_A()
    
    data /= numpy.amax(data)
    
    # make the time axis
    t = numpy.arange(len(data)) - len(data)/2
    t *= dt
    
    # fit the single pulse by convoluting it with itself and fitting it to the data
    A_out = MA.fit(t, data, fit_convolve, A)
    
    # calculate the fitted pulse and convoluted pulse
    y_single = pulse(A_out, t)
    y_conv = fit_convolve(A_out, t)

    # calculate the envelope
    sigma = A_out[0] 
    mu = A_out[1]
    offset = A_out[2] 
    scale = A_out[3] 
    A = [sigma, mu, offset, scale]
    y_env = envelope(A,t)

    # for the FWHM we need a higher time resolution
    t2 = numpy.arange(len(data)*10) - 5*len(data)
    t2 *= dt / 10
    y_fwhm = envelope(A,t2)
     # use the envelope to calculate the FWHM
    # make it positive
    if y_fwhm[int(len(t2)/2)] < 0:
        y_fwhm = -y_fwhm
    max_fwhm = numpy.amax(y_fwhm)
    # select the part of the list
    l = numpy.where(y_fwhm > max_fwhm/2)[0]
    # the length of the list in indices, multiply with time distance
    FWHM = len(l) * dt / 10
 
    if FWHM > fwhm_limit and flag_recursive_limit == False:
        # FWHM is above the limit, try again by shifting the mean a bit
        print("Trying again...")
        A = default_A()
        A[1] = mu_shift
        FWHM = calculate_pulse_length(data, A = A, dt = dt, plot_results = plot_results, print_results = print_results, flag_recursive_limit = True)
    
    else:
        # yay! a reasonable result. plot and print the results.
        if plot_results:
            plot_res(t, data, y_conv, y_single, y_env)
        if print_results:
            print_res(A_out, FWHM, dt)
    
    return FWHM
Ejemplo n.º 6
0
 def test_fit(self):
     x = numpy.arange(10)
     y = numpy.sin(x)
     A = [0,1,2,3]
     A = MATH.fit(x, y, EQ.rb_cos, A)
     print(A)