def local_fit(x, y, errors, mu, sigma): func = lambda x, mu, sigma, A, a0, a1: GAUSS(x, mu, sigma, A) + a0 + a1 * x fit = Fit(func) fit.mu = _simple_peak(y, mu, sigma) fit.sigma = sigma fit.A = y[fit.mu] fit.a0 = 0 fit.a1 = 0 for i in range(5): lower = max(fit.mu - 5 * fit.sigma, 0) upper = min(fit.mu + 5 * fit.sigma, len(x)) lx = x[lower:upper] ly = y[lower:upper] lerrors = errors[lower:upper] if i <= 2: fit.fit(lx, ly, lerrors, solver="curve_fit") else: fit.fit(lx, ly, lerrors, solver="minuit", method="migrad") return fit
def energieaufloesung(calibration, plot=True): print("##### ENERGY RESOLUTION #####") energies = [] widths = [] sigma_energies = [] sigma_widths = [] for filename, meta in kalib.items(): experiment = Experiment("data/" + filename, title=meta["title"], calibration=calibration) for peak in meta["peaks"]: mu0, sigma0 = peak[0], peak[1] fit = experiment.find_peak(mu0, sigma0, plot=False) energies.append(experiment.channel2energy(fit.mu)) widths.append(experiment.channelwidth2energywidth(fit.sigma)) sigma_energies.append( experiment.channelwidth2energywidth(fit.sigma_mu)) sigma_widths.append( experiment.channelwidth2energywidth(fit.sigma_sigma)) for filename, meta in data.items(): experiment = Experiment("data/" + filename, title=filename, calibration=calibration) experiment.subtract_empty("data/G20_Leer.mca", 0.5) for peak in meta["peaks"]: mu0, sigma0 = peak[0], peak[1] fit = experiment.find_peak(mu0, sigma0, plot=False) energies.append(experiment.channel2energy(fit.mu)) widths.append(experiment.channelwidth2energywidth(fit.sigma)) sigma_energies.append( experiment.channelwidth2energywidth(fit.sigma_mu)) sigma_widths.append( experiment.channelwidth2energywidth(fit.sigma_sigma)) energies = np.array(energies) widths = np.array(widths) sigma_energies = np.array(sigma_energies) sigma_widths = np.array(sigma_widths) X = energies Y = np.power(widths, 2) SX = sigma_energies SY = 2 * widths * sigma_widths func = lambda x, a0, a1, : a0 + x * a1 #+np.power(x,2)*a2 fit = Fit(func) fit.a0 = 1 fit.a1 = 1 for _ in range(10): err = fit.combine_errors(X, SX, SY) fit.fit(X, Y, err) if plot: plt.clf() plt.errorbar(X, Y, xerr=SX, yerr=SY, fmt=',') fit.plot(np.min(X), np.max(X), box='br', units={ 'a0': 'keV', 'a1': r'\sqrt{keV}' }) plt.xlabel(r"$ E $ / keV") plt.ylabel(r"$ \Delta E^2 / keV^2$") plt.title(r'Energieauflösung: Fit zu $ \Delta E^2 = a_0 + a_1 E $' ) # \oplus \frac{c}{E} plt.savefig("out/energyresolution_fit." + SAVETYPE) plt.clf() err = fit.combine_errors(X, SX, SY) fit.plot_residuums(X, Y, err, box='tr', fmt=",") plt.xlabel(r"$ E $ / keV") plt.ylabel(r"$ \Delta E^2 / keV^2$") plt.title("Energieauflösung: Residuen") plt.savefig("out/energyresolution_residuum." + SAVETYPE) with LatexTable("out/energyresolution.tex") as table: table.header("Parameter", "Wert") table.row("$a_0$", format_error(fit.a0, fit.sigma_a0, unit="keV^2")) table.row("$a_1$", format_error(fit.a1, fit.sigma_a1, unit="keV")) table.hline() a = math.sqrt(fit.a0) b = math.sqrt(fit.a1) sa = 0.5 * fit.sigma_a0 / a sb = 0.5 * fit.sigma_a1 / b table.row("$a$", format_error(a, sa, unit="keV")) table.row("$b$", format_error(b, sb, unit="\sqrt{keV}")) with LatexTable("out/energyresolution_examples.tex") as table: energies = np.linspace(10, 60, 6) sigmas = np.sqrt(fit.apply(energies)) deltas = sigmas * 2 * math.sqrt(2 * math.log(2)) table.header("Energie", "Auflösung", "Relative Auflösung", "FWHM", lineafter=0) table.row("$E$", "$\sigma$", "$\sigma / E$", "$2 \sqrt{2 \ln{2}} \sigma$") table.hline(2) for energy, sigma, delta in zip(energies, sigmas, deltas): e = "%d keV" % energy s = _n(sigma * 1000) + " eV" d = "%d eV" % (delta * 1000) table.row(e, s, _n(sigma / energy * 100) + r"\%", d)