Ejemplo n.º 1
0
def kr_bins(xxrange: Range = (-220, 220),
            yrange: Range = (-220, 220),
            zrange: Range = (100, 550),
            s2erange: Range = (3e3, 13e3),
            s1erange: Range = (1, 25),
            s2qrange: Range = (200, 800),
            xnbins: Int = 60,
            ynbins: Int = 60,
            znbins: Int = 12,
            s2enbins: Int = 50,
            s1enbins: Int = 10,
            s2qnbins: Int = 25) -> KrBins:

    Xbins = np.linspace(*xxrange, xnbins + 1)
    Ybins = np.linspace(*yrange, ynbins + 1)
    Xcenters = shift_to_bin_centers(Xbins)
    Ycenters = shift_to_bin_centers(Ybins)
    Xpitch = np.diff(Xbins)[0]
    Ypitch = np.diff(Ybins)[0]

    return KrBins(S2e=np.linspace(*s2erange, s2enbins + 1),
                  S1e=np.linspace(*s1erange, s1enbins + 1),
                  S2q=np.linspace(*s2qrange, s2qnbins + 1),
                  X=Xbins,
                  Y=Ybins,
                  Z=np.linspace(*zrange, znbins + 1),
                  Xc=Xcenters,
                  Yc=Ycenters,
                  Xp=Xpitch,
                  Yp=Ypitch,
                  T=None)
Ejemplo n.º 2
0
def kr_bins(Zrange=(100, 550),
            XYrange=(-220, 220),
            Erange=(2e3, 15e3),
            S1range=(0, 50),
            Qrange=(100, 1500),
            Znbins=10,
            XYnbins=30,
            Enbins=50,
            S1nbins=10,
            Qnbins=25):

    Zbins = np.linspace(*Zrange, Znbins + 1)
    Ebins = np.linspace(*Erange, Enbins + 1)
    S1bins = np.linspace(*S1range, S1nbins + 1)
    Qbins = np.linspace(*Qrange, Qnbins + 1)
    XYbins = np.linspace(*XYrange, XYnbins + 1)
    XYcenters = shift_to_bin_centers(XYbins)
    XYpitch = np.diff(XYbins)[0]

    exyzBins = ExyzBins(E=Ebins,
                        S1=S1bins,
                        Q=Qbins,
                        Z=Zbins,
                        XY=XYbins,
                        cXY=XYcenters,
                        pXY=XYpitch)

    return exyzBins
Ejemplo n.º 3
0
def h1d(x,
        bins=None,
        range=None,
        xlabel='Variable',
        ylabel='Number of events',
        title=None,
        legend='upper right',
        weights=None,
        ax=None):

    if ax is None:
        fig = plt.figure(figsize=figsize)
        ax = fig.add_subplot(1, 1, 1)
    if weights is None:
        weights = [1.] * len(x)

    ax.set_xlabel(xlabel)  #,fontsize = 11)
    ax.set_ylabel(ylabel)  #, fontsize = 11)
    yhist, xhist, _ = ax.hist(x,
                              bins=bins,
                              range=range,
                              histtype='step',
                              edgecolor='black',
                              linewidth=1.5,
                              weights=weights,
                              rasterized=True)
    plt.grid(True)

    if title:
        plt.title(title)

    return yhist, shift_to_bin_centers(xhist)
Ejemplo n.º 4
0
def fit_energy(e : np.array,
               nbins   : int,
               range   : Tuple[float],
               n_sigma : float = 3.0)->FitCollection:
    """
    Takes an "energy vector" (e.g, 1d array), with number of bins enbins and range erange, then:
        1. Computes the histogram of e with enbins in erange. This returns an array of bin
        edges (b), and bin contents (y). The array (b) is shifted to bin centers (x)
        2. The arrays x and y are fitted to a gaussian, in a range given by an interval
        arround the estimation of the maximum of the gaussian. The interval size is estimated
        by multiplying n_sigma by the estimation of the gaussian std.

    The result of the fit is a fit collection, that includes a FitPar and a HistoPar objects
    needed for printing and plotting the fit result.
       """

    y, b = np.histogram(e, bins= nbins, range=range)
    x = shift_to_bin_centers(b)
    bin_size = (range[1] - range[0]) / nbins
    seed = gaussian_parameters(e, range, bin_size)

    fp, fr = gaussian_fit(x, y, seed, n_sigma)

    hp = HistoPar(var      = e,
                  nbins    = nbins,
                  range    = range)

    return FitCollection(fp = fp, hp = hp, fr = fr)
Ejemplo n.º 5
0
def get_time_series_df(time_bins    : Number,
                       time_range   : Tuple[float, float],
                       dst          : DataFrame,
                       time_column  : str = 'DT')->Tuple[np.array, List[np.array]]:
    """

    Given a dst (DataFrame) with a time column specified by the name time,
    this function returns a time series (ts) and a list of masks which are used to divide
    the event in time tranches.

    More generically, one can produce a "time series" using any column of the dst
    simply specifying time_column = ColumName

        Parameters
        ----------
            time_bins
                Number of time bines.
            time_range
                Time range.
            dst
                A Data Frame
            time_column
            A string specifyng the dst column to be divided in time slices.

        Returns
        -------
            A Tuple with:
            np.array       : This is the ts vector
            List[np.array] : This are the list of masks defining the events in the time series.

    """
    nt = time_bins
    ip = np.linspace(time_range[0], time_range[-1], time_bins+1)
    masks = np.array([in_range(dst[time_column].values, ip[i], ip[i + 1]) for i in range(len(ip) -1)])
    return shift_to_bin_centers(ip), masks
Ejemplo n.º 6
0
def fit_s2_energy_in_z_bins_within_XY_limits(
    kre: KrEvent,
    kL: KrRanges,
    kNB: KrNBins,
    kB: KrBins,
    eR: Ranges,
    figsize=(12, 12)) -> KrFit:
    fig = plt.figure(figsize=figsize)  # Creates a new figure
    EMU = []
    ES = []
    CHI2 = []

    for j, i in enumerate(range(kNB.Z)):
        ax = fig.add_subplot(5, 2, i + 1)
        ax.set_xlabel('S2 energy (pes)', fontsize=11)  #xlabel
        ax.set_ylabel('Number of events', fontsize=11)  #ylabel

        zlim = kB.Z[i], kB.Z[i + 1]

        sel = in_range(kre.X, *kL.XY) & in_range(kre.Y, *kL.XY) & in_range(
            kre.Z, *zlim)
        e = kre.E[sel]

        print(
            f'bin : {j}, energy range for fit: lower = {eR.lower[j]}, upper = {eR.upper[j]}'
        )
        sel = in_range(e, eR.lower[j], eR.upper[j])
        er = e[sel]

        y, b, _ = ax.hist(er,
                          bins=kB.E,
                          histtype='step',
                          edgecolor='black',
                          linewidth=1.5)

        x = shift_to_bin_centers(b)

        df = pd.DataFrame(dict(y=y, x=x))
        df = df[df.y > 0]
        fit_range = (df.x.values[0], df.x.values[-1])
        x = df.x.values
        y = df.y.values
        yu = np.sqrt(y)

        seed = gauss_seed(x, y)
        f = fitf.fit(fitf.gauss, x, y, seed, fit_range=fit_range, sigma=yu)
        plt.plot(x, f.fn(x), "r-", lw=4)

        EMU.append(f.values[1])
        ES.append(f.errors[1])
        CHI2.append(chi2(f, x, y, yu))

        plt.grid(True)
    plt.tight_layout()

    return KrFit(par=np.array(EMU),
                 err=np.array(ES),
                 chi2=np.array(CHI2),
                 valid=np.ones(len(EMU)))
Ejemplo n.º 7
0
def kr_times_ranges_and_bins(dst,
                             Zrange=(100, 550),
                             XYrange=(-220, 220),
                             Erange=(2e3, 15e3),
                             S1range=(0, 50),
                             Qrange=(100, 1500),
                             Znbins=10,
                             XYnbins=30,
                             Enbins=50,
                             S1nbins=10,
                             Qnbins=25,
                             nStimeprofile=3600):

    Zbins = np.linspace(*Zrange, Znbins + 1)
    Ebins = np.linspace(*Erange, Enbins + 1)
    S1bins = np.linspace(*S1range, S1nbins + 1)
    Qbins = np.linspace(*Qrange, Qnbins + 1)
    XYbins = np.linspace(*XYrange, XYnbins + 1)
    XYcenters = shift_to_bin_centers(XYbins)
    XYpitch = np.diff(XYbins)[0]

    dst_time = dst.sort_values('event')
    T = dst_time.time.values
    tstart = T[0]
    tfinal = T[-1]
    Trange = (datetime.datetime.fromtimestamp(tstart),
              datetime.datetime.fromtimestamp(tfinal))

    ntimebins = int(np.floor((tfinal - tstart) / nStimeprofile))
    Tnbins = np.max([ntimebins, 1])
    Tbins = np.linspace(tstart, tfinal, ntimebins + 1)

    krNBins = KrNBins(E=Enbins,
                      S1=S1nbins,
                      Q=Qnbins,
                      Z=Znbins,
                      XY=XYnbins,
                      T=Tnbins)
    krRanges = KrRanges(E=Erange,
                        S1=S1range,
                        Q=Qrange,
                        Z=Zrange,
                        XY=XYrange,
                        T=Trange)
    krBins = KrBins(E=Ebins,
                    S1=S1bins,
                    Q=Qbins,
                    Z=Zbins,
                    XY=XYbins,
                    cXY=XYcenters,
                    T=Tbins)

    times = [np.mean([Tbins[t], Tbins[t + 1]]) for t in range(Tnbins)]
    TL = [(Tbins[t], Tbins[t + 1]) for t in range(Tnbins)]
    timeStamps = list(map(datetime.datetime.fromtimestamp, times))
    krTimes = KrTimes(times=times, timeStamps=timeStamps, TL=TL)

    return krTimes, krRanges, krNBins, krBins
Ejemplo n.º 8
0
def fit_lifetime(kB, kf, title="Lifetime Fit"):
    x = shift_to_bin_centers(kB.Z)
    y = kf.par
    yu = kf.err
    plt.errorbar(x, y, yu, np.diff(x)[0] / 2, fmt="kp", ms=7, lw=3)
    seed = expo_seed(x, y)
    f = fitf.fit(fitf.expo, x, y, seed, sigma=yu)
    plt.plot(x, f.fn(x), "r-", lw=4)
    print_fit(f)
    print('chi2 = {}'.format(chi2(f, x, y, yu)))
Ejemplo n.º 9
0
def quick_gauss_fit(data, bins):
    """
    Histogram input data and fit it to a gaussian with the parameters
    automatically estimated.
    """
    y, x  = np.histogram(data, bins)
    x     = shift_to_bin_centers(x)
    seed  = gauss_seed(x, y)
    f     = fitf.fit(fitf.gauss, x, y, seed)
    assert np.all(f.values != seed)
    return f
Ejemplo n.º 10
0
def main():
    """ Basic plot of event rate """

    # bin width in seconds
    bin_width = int(sys.argv[2])
    max_evt = np.inf
    if len(sys.argv) > 3:
        max_evt = int(sys.argv[3])
    hist_end = int(datetime.now().timestamp())
    bins_def = False
    bins = None
    stamp_hist = None
    nevt = 0
    true_last = 0
    for fileName in iglob(sys.argv[1]+'*_waveforms.h5'):
        if nevt < max_evt:
            with tb.open_file(fileName, 'r') as dataF:
                timestamps = np.fromiter((evt[1]/1000 for evt in dataF.root.Run.events), np.int)
                nevt += len(timestamps)
                if not bins_def:
                #start time in seconds
                    start_time = int(timestamps[0])
                    bins = np.arange(start_time, hist_end, bin_width)
                    stamp_hist = np.zeros(len(bins)-1, dtype=np.int)
                    bins_def = True
           
                # Ignore last bin as probably not equal width
                true_last = max(true_last, np.argwhere(bins>timestamps[-1])[0][0])-1
                stamp_hist += np.histogram(timestamps, bins)[0]

    print('check: ', datetime.fromtimestamp(shift_to_bin_centers(bins)[0]))
    ## Convert to human readable
    bins = shift_to_bin_centers(bins)[:true_last]
    dates = [ datetime.fromtimestamp(t) for t in bins ]
    plt.plot(dates, stamp_hist[:true_last]/bin_width)
    plt.title('Trigger rate in bins of '+str(bin_width/60)+' minutes')
    plt.xlabel('Timestamp (s)')
    plt.ylabel('events per second')
    plt.show()
Ejemplo n.º 11
0
def compute_drift_v(zdata: np.array,
                    nbins: int = 35,
                    zrange: Tuple[float, float] = (500, 640),
                    seed: Tuple[float, float, float, float] = None,
                    detector: str = 'new',
                    plot_fit: bool = False) -> Tuple[float, float]:
    """
    Computes the drift velocity for a given distribution
    using the sigmoid function to get the cathode edge.

    Parameters
    ----------
    zdata: array_like
        Values of Z coordinate.
    nbins: int (optional)
        The number of bins in the z coordinate for the binned fit.
    zrange: length-2 tuple (optional)
        Fix the range in z.
    seed: length-4 tuple (optional)
        Seed for the fit.
    detector: string (optional)
        Used to get the cathode position from DB.
    plot_fit: boolean (optional)
        Flag for plotting the results.

    Returns
    -------
    dv: float
        Drift velocity.
    dvu: float
        Drift velocity uncertainty.
    """

    y, x = np.histogram(zdata, nbins, zrange)
    x = shift_to_bin_centers(x)

    if seed is None: seed = np.max(y), np.mean(zrange), 0.5, np.min(y)

    f = fitf.fit(sigmoid, x, y, seed, sigma=poisson_sigma(y), fit_range=zrange)

    z_cathode = DB.DetectorGeo(detector).ZMAX[0]
    dv = z_cathode / f.values[1]
    dvu = dv / f.values[1] * f.errors[1]

    if plot_fit:
        plt.figure()
        plt.hist(zdata, nbins, zrange)
        xx = np.linspace(zrange[0], zrange[1], nbins)
        plt.plot(xx, sigmoid(xx, *f[1]), color='red')

    return dv, dvu
Ejemplo n.º 12
0
def selection_in_band(
    z: np.array,
    e: np.array,
    range_z: Range,
    range_e: Range,
    nbins_z: int = 50,
    nbins_e: int = 100,
    nsigma: float = 3.5
) -> Tuple[np.array, FitPar, FitPar, HistoPar2, ProfilePar]:
    """ This returns a selection of the events that are inside the Kr E vz Z
    returns: np.array(bool)
    """

    zbins = np.linspace(*range_z, nbins_z + 1)
    zerror = np.diff(zbins) * 0.5
    ebins = np.linspace(*range_e, nbins_e + 1)
    zc = shift_to_bin_centers(zbins)

    sel_e = in_range(e, *range_e)
    mean, sigma, chi2, ok = fit_slices_1d_gauss(z[sel_e],
                                                e[sel_e],
                                                zbins,
                                                ebins,
                                                min_entries=5e2)
    e_mean = mean.value
    e_sigma = sigma.value
    # 1. Profile of mean values of e in bins of z
    #zc, e_mean, e_sigma = fitf.profileX(z, e, nbins_z, range_z, range_e)

    #2. Fit two exponentials to e_mmean +- ns_igma * e_sigma defining a band

    y = e_mean + nsigma * e_sigma
    fph, _, _ = fit_lifetime_unbined(zc, y, nbins_z, range_z)
    y = e_mean - nsigma * e_sigma
    fpl, _, _ = fit_lifetime_unbined(zc, y, nbins_z, range_z)

    # 3. Select events in the range defined by the band

    sel_inband = in_range(e, fpl.f(z), fph.f(z))

    # return data
    hp = HistoPar2(var=z,
                   nbins=nbins_z,
                   range=range_z,
                   var2=e,
                   nbins2=nbins_e,
                   range2=range_e)

    pp = ProfilePar(x=zc, xu=zerror, y=e_mean, yu=e_sigma)

    return sel_inband, fpl, fph, hp, pp
Ejemplo n.º 13
0
def energy_in_XYRange(kre: KrEvent, xr: Tuple[float], yr: Tuple[float],
                      ernb: ExyzNBins) -> KrFit:

    sel = in_range(kre.X, *xr) & in_range(kre.Y, *yr)
    e = kre.E[sel]
    bins = ernb.E
    frame_data = plt.gcf().add_axes((.1, .3, .8, .6))

    y, b, _ = plt.hist(e,
                       bins=bins,
                       histtype='step',
                       edgecolor='black',
                       linewidth=1.5)
    x = shift_to_bin_centers(b)

    seed = gauss_seed(x, y)
    fit_range = seed[1] - 2.0 * seed[2], seed[1] + 2.0 * seed[2]
    x, y = x[in_range(x, *fit_range)], y[in_range(x, *fit_range)]
    f = fitf.fit(fitf.gauss, x, y, seed, sigma=poisson_sigma(y))

    yu = poisson_sigma(y)
    plt.plot(x, f.fn(x), "r-", lw=4)

    frame_data.set_xticklabels([])
    labels("", "Entries", "Energy fit example")
    lims = plt.xlim()

    frame_res = plt.gcf().add_axes((.1, .1, .8, .2))
    plt.errorbar(x, (f.fn(x) - y) / yu, 1, np.diff(x)[0] / 2, fmt="p", c="k")
    plt.plot(lims, (0, 0), "g--")
    plt.xlim(*lims)
    plt.ylim(-5, +5)

    kf = KrFit(par=np.array(f.values),
               err=np.array(f.errors),
               chi2=chi2(f, x, y, yu))
    return kf
Ejemplo n.º 14
0
def selection_in_band(E,
                      Z,
                      Erange,
                      Zrange,
                      Zfitrange,
                      nsigma=3.5,
                      Znbins=50,
                      Enbins=100,
                      plot=True):
    """ This returns a selection of the events that are inside the Kr E vz Z
    returns: np.array(bool)
        If plot=True, it draws E vs Z and the band
    """
    Zfit = Zfitrange

    Zbins = np.linspace(*Zrange, Znbins + 1)
    Ebins = np.linspace(*Erange, Enbins + 1)

    Zcenters = shift_to_bin_centers(Zbins)
    Zerror = np.diff(Zbins) * 0.5

    sel_e = in_range(E, *Erange)
    mean, sigma, chi2, ok = fit_slices_1d_gauss(Z[sel_e],
                                                E[sel_e],
                                                Zbins,
                                                Ebins,
                                                min_entries=5e2)
    ok = ok & in_range(Zcenters, *Zfit)

    def _line_cut(sign):
        x = Zcenters[ok]
        y = mean.value[ok] + sign * nsigma * sigma.value[ok]
        yu = mean.uncertainty[ok]
        seed = expo_seed(x, y)
        efit = fitf.fit(fitf.expo, x, y, seed, sigma=yu)
        assert np.all(efit.values != seed)
        return efit.fn

    lowE_cut = _line_cut(-1.)
    highE_cut = _line_cut(+1.)

    sel_inband = in_range(E, lowE_cut(Z), highE_cut(Z))

    if (plot == False): return sel_inband

    plt.hist2d(Z, E, (Zbins, Ebins), cmap=default_cmap)
    plt.errorbar(Zcenters[ok],
                 mean.value[ok],
                 sigma.value[ok],
                 Zerror[ok],
                 "kp",
                 label="Kr peak energy $\pm 1 \sigma$")
    f = fitf.fit(fitf.expo, Zcenters[ok], mean.value[ok], (1e4, -1e3))
    plt.plot(Zcenters, f.fn(Zcenters), "r-")
    print(f.values)
    plt.plot(Zbins,
             lowE_cut(Zbins),
             "m",
             lw=2,
             label="$\pm " + str(nsigma) + " \sigma$ region")
    plt.plot(Zbins, highE_cut(Zbins), "m", lw=2)
    plt.legend()
    labels("Drift time (µs)", "S2 energy (pes)", "Energy vs drift")

    return sel_inband
Ejemplo n.º 15
0
def relative_pmt_response():
    """
    Script which uses pmaps (will be generalised in future to check XY dependence)
    to look at the relative response of the PMTs in Kr events and
    compares to the results on Poisson mu from calibrations
    """

    pmap_file_base = sys.argv[1]
    dst_file_base = sys.argv[2]

    run_number = pmap_file_base.split('/')[2][1:]

    pmt_dats = DB.DataPMT(int(run_number))

    s1hists = {x: [] for x in range(12)}
    s2hists = {x: [] for x in range(12)}
    s1sumh = []
    s2sumh = []
    hitPMTdist = {x: [] for x in range(12)}
    hitPMTZpos = {x: [] for x in range(12)}

    pmap_sorter = sorter_func(pmap_file_base)
    pmap_file_list = sorted(glob(pmap_file_base + '*.h5'), key=pmap_sorter)

    dst_sorter = sorter_func(dst_file_base)
    dst_file_list = sorted(glob(dst_file_base + '*.h5'), key=dst_sorter)

    ## dst_frame = load_dsts(dst_file_list, 'DST', 'Events')
    dst_frame = load_dsts(dst_file_list, 'RECO', 'Events')

    dst_evt_list = dst_frame['event'].unique()

    #for fn in iglob(pmap_file_base + '*.h5'):
    for fn in pmap_file_list:

        ## This version just using pmt databases
        s1df, s2df, _, s1pmtdf, s2pmtdf = load_pmaps_as_df(fn)

        common_evts = np.intersect1d(s1pmtdf['event'].unique(), dst_evt_list)

        for evt in common_evts:
            #for evt in s1pmtdf['event'].unique():
            #evt    = dst_evt_iter[0]
            s1evt = s1pmtdf[s1pmtdf['event'] == evt]
            s2evt = s2pmtdf[s2pmtdf['event'] == evt]
            s1sevt = s1df[s1df['event'] == evt]
            s2sevt = s2df[s2df['event'] == evt]
            hit_evt = dst_frame[dst_frame['event'] == evt]
            ## if hit_evt['nS2'].iloc[0] == 1 and len(s2evt['peak'].unique()) == 1 and len(s1evt['peak'].unique()) == 1:
            if hit_evt['npeak'].nunique() == 1 and len(
                    s2evt['peak'].unique()) == 1 and len(
                        s1evt['peak'].unique()) == 1:
                ## Not well defined for multi-S2 events
                hit_x = hit_evt['X'].iloc[0]
                hit_y = hit_evt['Y'].iloc[0]
                hit_z = hit_evt['Z'].iloc[0]
                for peak in s1evt['peak'].unique():
                    s1peak = s1evt[s1evt['peak'] == peak]
                    s1sumh.append(s1sevt[s1sevt['peak'] == peak]['ene'].sum())
                    pmt1Q = s1peak[s1peak['npmt'] == 1]['ene'].sum()
                    for pmt in s1peak['npmt'].unique():
                        hitPMTdist[pmt].append(
                            np.sqrt(
                                np.power(
                                    hit_x - pmt_dats[pmt_dats['SensorID'] ==
                                                     pmt].X.values, 2) +
                                np.power(
                                    hit_y - pmt_dats[pmt_dats['SensorID'] ==
                                                     pmt].Y.values, 2)))
                        hitPMTZpos[pmt].append(hit_z)
                        if pmt != 1:
                            s1hists[pmt].append(
                                s1peak[s1peak['npmt'] == pmt]['ene'].sum() /
                                pmt1Q)
                        else:
                            s1hists[pmt].append(pmt1Q)

                for peak in s2evt['peak'].unique():
                    s2peak = s2evt[s2evt['peak'] == peak]
                    s2sumh.append(s2sevt[s2sevt['peak'] == peak]['ene'].sum())
                    if s2sumh[-1] > 4000:  # and s2sumh[-1] < 12000:
                        ## pmt1Q = s2peak[s2peak['npmt'] == 1]['ene'].values[5:-5]
                        pmt1Q = s2peak[s2peak['npmt'] == 1]['ene'].sum()
                        for pmt in s2peak['npmt'].unique():
                            if pmt != 1:
                                ## s2hists[pmt].append(s2peak[s2peak['npmt'] == pmt]['ene'].values[5:-5]/pmt1Q)
                                s2hists[pmt].append(
                                    s2peak[s2peak['npmt'] == pmt]['ene'].sum()
                                    / pmt1Q)
                            else:
                                s2hists[pmt].append(pmt1Q)

            #dst_evt_iter.iternext()

    ## Make the plots
    s1sumh = np.array(s1sumh)
    s2sumh = np.array(s2sumh)
    figs0, axes0 = plt.subplots(nrows=1, ncols=2)
    axes0[0].hist(s1sumh)
    axes0[0].set_title('PMT sum S1 distribution')
    axes0[1].hist(s2sumh)
    axes0[1].set_title('PMT sum S2 distribution')
    plt.tight_layout()
    figs0.show()
    figs0.savefig('SumChargescharge_R' + run_number + '.png')
    figs1, axess1 = plt.subplots(nrows=3, ncols=4, figsize=(20, 6))
    s1pmt1 = np.array(s1hists[1])
    s1bins = np.arange(-2, 4, 0.1)
    s2bins = np.arange(0.4, 1.1, 0.005)
    s1select = (s1sumh > 2) & (s1sumh < 150)
    for (key, val), ax in zip(s1hists.items(), axess1.flatten()):
        if key == 1:
            ax.hist(np.array(val)[s1select], bins=100)
            #ax.scatter(s1sumh[s1select], np.array(val)[s1select])
            ## ax.scatter(np.array(hitPMTdist[key])[s1select], np.array(val)[s1select])
            #ax.scatter(np.array(hitPMTZpos[key])[s1select], np.array(val)[s1select])
            ax.set_title('PMT 1 S1 charge')
            #ax.set_xlabel('integrated charge in PMT sum (pe)')
            #ax.set_xlabel('z pos.')
            #ax.set_ylabel('integrated charge in PMT1 (pe)')
            ax.set_ylabel('AU)')
            ax.set_xlabel('integrated charge in PMT1 (pe)')
            sh_hits = np.array(hitPMTZpos[key])[s1select].shape
            sh_val = np.array(val)[s1select].shape
            covar = np.cov(
                np.array(hitPMTZpos[key])[s1select].reshape(1, sh_hits[0]),
                np.array(val)[s1select].reshape(1, sh_val[0]))[0, 1]
            corr_coef = covar / (
                np.std(np.array(val)[s1select], ddof=1) *
                np.std(np.array(hitPMTZpos[key])[s1select], ddof=1))
            print('Sensor ', key, ' correlation coefficient = ', corr_coef)
        else:
            vals, bins, _ = ax.hist(np.array(val)[s1select], bins=s1bins)
            ## ax.scatter(s1pmt1[np.abs(val) < 10], np.array(val)[np.abs(val) < 10])
            #ax.scatter(s1sumh[s1select], np.array(val)[s1select])
            ## ax.scatter(np.array(hitPMTdist[key])[s1select & (np.abs(val) < 10)], np.array(val)[s1select & (np.abs(val) < 10)])
            #ax.scatter(np.array(hitPMTZpos[key])[s1select & (np.abs(val) < 10)], np.array(val)[s1select & (np.abs(val) < 10)])
            ax.set_title('PMT ' + str(key) + ' S1 relative charge')
            #ax.set_xlabel('integrated charge in PMT sum (pe)')
            ## ax.set_xlabel('PMT-hit dist. (mm)')
            #ax.set_xlabel('hit Z pos')
            #ax.set_ylabel('pmt q / pmt1 q')
            ax.set_ylabel('AU')
            ax.set_xlabel('pmt q / pmt1 q')
            ## sh_hits = np.array(hitPMTZpos[key])[s1select].shape
            ## sh_val = np.array(val)[s1select].shape
            ## covar = np.cov(np.array(hitPMTZpos[key])[s1select].reshape(1, sh_hits[0]), np.array(val)[s1select].reshape(1, sh_val[0]))[0, 1]
            ## corr_coef = covar / (np.std(np.array(val)[s1select], ddof=1)*np.std(np.array(hitPMTZpos[key])[s1select], ddof=1))
            s1select2 = s1select & (np.array(val) > 0) & (np.array(val) <= 2)
            print('Sensor ', key, ' mean = ',
                  np.mean(np.array(val)[s1select2]))
            useful_bins = np.argwhere(vals >= 100)
            b1 = useful_bins[0][0]
            b2 = useful_bins[-1][0]
            errs = np.sqrt(vals[b1:b2])
            fvals = fitf.fit(fitf.gauss,
                             shift_to_bin_centers(bins)[b1:b2],
                             vals[b1:b2],
                             seed=(vals.sum(), bins[vals.argmax()], 0.1),
                             sigma=errs)
            ax.plot(
                shift_to_bin_centers(bins)[b1:b2],
                fvals.fn(shift_to_bin_centers(bins)[b1:b2]))
            print('Fit S1 ' + str(key), fvals.values, fvals.errors, fvals.chi2)
    plt.tight_layout()
    figs1.show()
    figs1.savefig('s1relativechargeThzoom_R' + run_number + '.png')

    fitVals = {}
    figs2, axess2 = plt.subplots(nrows=3, ncols=4, figsize=(20, 6))
    s2pmt1 = np.array(s2hists[1])
    for (key, val), ax in zip(s2hists.items(), axess2.flatten()):
        if key == 1:
            ## ax.set_title('PMT 1 S2 charge')
            ax.set_title('PMT 1 S2 charge vs s2 sum charge')
            ax.set_xlabel('S2pmt sum charge (pe)')
            #ax.set_xlabel('integrated charge in PMT sum (pe)')
            #ax.set_xlabel('z pos')
            ax.set_ylabel('integrated charge in PMT1 (pe)')
            #ax.set_ylabel('AU')
            ax.set_xlabel('integrated charge in PMT1 (pe)')
            ## ax.hist(np.array(val)[(s2sumh>4000) & (s2sumh<12000)], bins=100)
            ##ax.hist(np.concatenate(val), bins=100)
            ## ax.hist(np.array(val)[s2sumh>4000], bins=100)
            ax.scatter(s2sumh[s2sumh > 4000], np.array(val)[s2sumh > 4000])
            #ax.scatter(s2sumh[(s2sumh>4000) & (s2sumh<12000)], np.array(val)[(s2sumh>4000) & (s2sumh<12000)])
            ## ax.scatter(np.array(hitPMTdist[key])[(s2sumh>4000) & (s2sumh<12000)], np.array(val)[(s2sumh>4000) & (s2sumh<12000)])
            #ax.scatter(np.array(hitPMTZpos[key])[(s2sumh>4000) & (s2sumh<12000)], np.array(val)[(s2sumh>4000) & (s2sumh<12000)])
            ## sh_hits = np.array(hitPMTdist[key])[(s2sumh>4000) & (s2sumh<12000)].shape
            ## sh_val = np.array(val)[(s2sumh>4000) & (s2sumh<12000)].shape
            ## covar = np.cov(np.array(hitPMTdist[key])[(s2sumh>4000) & (s2sumh<12000)].reshape(1, sh_hits[0]), np.array(val)[(s2sumh>4000) & (s2sumh<12000)].reshape(1, sh_val[0]))[0, 1]
            ## corr_coef = covar / (np.std(np.array(val)[(s2sumh>4000) & (s2sumh<12000)], ddof=1)*np.std(np.array(hitPMTdist[key])[(s2sumh>4000) & (s2sumh<12000)], ddof=1))
            ## print('Sensor ', key, ' correlation coefficient = ', corr_coef)
        else:
            ## ax.set_title('PMT '+str(key)+' S2 relative charge')
            ax.set_title('PMT ' + str(key) + ' S2 relative charge vs pmt sum')
            ax.set_ylabel('pmt q / pmt1 q')
            #ax.set_xlabel('zpos')
            ax.set_xlabel('integrated charge in PMT sum (pe)')
            #ax.set_xlabel('pmt q / pmt1 q')
            #ax.set_ylabel('AU')
            #ax.scatter(s2pmt1[np.abs(val) < 10], np.array(val)[np.abs(val) < 10])
            #ax.scatter(s2sumh[(s2sumh>4000) & (s2sumh<12000)], np.array(val)[(s2sumh>4000) & (s2sumh<12000)])
            ## vals, bins, _ = ax.hist(np.array(val)[(s2sumh>4000) & (s2sumh<12000)], bins=s2bins)
            ## vals, bins, _ = ax.hist(np.concatenate(val), bins=s2bins)
            ## vals, bins, _ = ax.hist(np.array(val)[s2sumh>4000], bins=s2bins)
            ax.scatter(s2sumh[s2sumh > 4000], np.array(val)[s2sumh > 4000])
            ## ax.scatter(np.array(hitPMTdist[key])[(s2sumh>4000) & (s2sumh<12000)], np.array(val)[(s2sumh>4000) & (s2sumh<12000)])
            #ax.scatter(np.array(hitPMTZpos[key])[(s2sumh>4000) & (s2sumh<12000)], np.array(val)[(s2sumh>4000) & (s2sumh<12000)])
            sh_sum = s2sumh[s2sumh > 4000].shape
            sh_vals = np.array(val)[s2sumh > 4000].shape
            covar = np.cov(s2sumh[s2sumh > 4000].reshape(1, sh_sum[0]),
                           np.array(val)[s2sumh > 4000].reshape(1,
                                                                sh_vals[0]))[0,
                                                                             1]
            corr_coef = covar / (np.std(np.array(val)[s2sumh > 4000], ddof=1) *
                                 np.std(s2sumh[s2sumh > 4000], ddof=1))
            ## sh_hits = np.array(hitPMTdist[key])[(s2sumh>4000) & (s2sumh<12000)].shape
            ## sh_val = np.array(val)[(s2sumh>4000) & (s2sumh<12000)].shape
            ## covar = np.cov(np.array(hitPMTdist[key])[(s2sumh>4000) & (s2sumh<12000)].reshape(1, sh_hits[0]), np.array(val)[(s2sumh>4000) & (s2sumh<12000)].reshape(1, sh_val[0]))[0, 1]
            ## corr_coef = covar / (np.std(np.array(val)[(s2sumh>4000) & (s2sumh<12000)], ddof=1)*np.std(np.array(hitPMTdist[key])[(s2sumh>4000) & (s2sumh<12000)], ddof=1))
            print('Sensor ', key, ' correlation coefficient = ', corr_coef)
            ## limit fit to region with stat error <= 10% Poisson
            ## useful_bins = np.argwhere(vals>=200)
            ## b1 = useful_bins[0][0]
            ## b2 = useful_bins[-1][0]
            ## errs = np.sqrt(vals[b1:b2])
            ## print('Seed check: ', (vals.sum(), bins[vals.argmax()], 0.02))
            ## fvals = fitf.fit(fitf.gauss, shift_to_bin_centers(bins)[b1:b2], vals[b1:b2],
            ##                  seed=(vals.sum(), bins[vals.argmax()], 0.02),
            ##                  sigma=errs, bounds=[(0, 0, 0.00001), (1e10, 2, 3)])
            ## ax.plot(shift_to_bin_centers(bins),
            ##         fitf.gauss(shift_to_bin_centers(bins), *fvals.values))
            ## fitVals[key] = (fvals.values[1], fvals.values[2])
            ## print('Fit PMT '+str(key), fvals.values, fvals.errors, fvals.chi2)
    plt.tight_layout()
    figs2.show()
    figs2.savefig('s2relativechargeThvsSum_R' + run_number + '.png')

    ## figcal, axcal = plt.subplots()
    ## axcal.errorbar(list(fitVals.keys()),
    ##                np.fromiter((x[0] for x in fitVals.values()), np.float),
    ##                yerr=np.fromiter((x[1] for x in fitVals.values()), np.float),
    ##                label='Average response of PMTs to Kr relative to PMT 1')
    ## ## Get the calibration info for comparison.
    ## cal_files = [ fname for fname in sys.argv[3:] ]
    ## read_params = partial(spr, table_name='FIT_pmt_scaled_dark_pedestal',
    ##                       param_names=['poisson_mu'])
    ## ## Assumes ordering, ok?
    ## for i, fn in enumerate(cal_files):
    ##     cal_run = fn.split('_')[1]
    ##     with tb.open_file(fn) as cal_in:
    ##         pmt1Val = 0
    ##         pmt1Err = 0
    ##         cVals = []
    ##         cErrs = []
    ##         for sens, (pars, errs) in read_params(cal_in):
    ##             if sens != 1:
    ##                 cVals.append(pars['poisson_mu'])
    ##                 cErrs.append(errs['poisson_mu'])
    ##             else:
    ##                 pmt1Val = pars['poisson_mu']
    ##                 pmt1Err = errs['poisson_mu']
    ##         normVals = np.array(cVals) / pmt1Val
    ##         normErrs = normVals * np.sqrt(np.power(np.array(cErrs)/np.array(cVals), 2) +
    ##                                       np.power(pmt1Err/pmt1Val, 2))
    ##         axcal.errorbar(list(fitVals.keys()), normVals,
    ##                        yerr=normErrs, label='Calibration '+cal_run)
    ## axcal.legend()
    ## axcal.set_xlabel('PMT sensor ID')
    ## axcal.set_ylabel('Response relative to that of PMT 1')
    ## figcal.show()
    ## figcal.savefig('calPoisKrRelCompStatsFILT.png')
    input('plots good?')
Ejemplo n.º 16
0
def plot_residuals_E_reso_gauss(energy, e_nbins, e_range, mu, mu_u , sigma, sigma_u, N,N_u, name_fig):
    
    import seaborn as sns
    sns.set()
    sns.set_style("white")
    sns.set_style("ticks")

    fig = plt.figure(figsize=(9,7))
    global_linewidth    = 2
    global_linecolor    = "r" 
    
    # compute y values from histogram
    e_bins       =  np.linspace(*  e_range   ,   e_nbins + 1)
    entries, e   =  np.histogram(energy, e_bins)
    e            =  shift_to_bin_centers(e)
    e_u          =  np.diff(e)[0] * 0.5
    #entries_u    =  poisson_sigma(entries)
    entries_u    =  entries**0.5
    
    # compute residuals
    scale = (e_range[1] - e_range[0])/e_nbins
#    print(scale)
    y_from_fit    = mypdf_gauss(e, mu, sigma, N*scale )
    residuals     = (y_from_fit - entries)/ entries_u
    
    # Plot
    frame_data = plt.gcf().add_axes((.1, .3,.8, .6))
    
    plt.errorbar    (e, entries, entries_u, 0, "p", c="k")
    plt.plot        (e, y_from_fit, lw=global_linewidth, color=global_linecolor   )
    
    leg1 = plt.gca().legend(('fit', 'data'), loc='upper right')


    # compute resolution
    resolution = 235*sigma/mu
    
    textstr = '\n'.join((
        '$\mu={:.2f}      \pm {:.2f} $'     .format(mu,mu_u),
        '$\sigma 1={:.2f} \pm {:.2f}$'      .format(sigma, sigma_u),
        '$N ={:.2f}      \pm {:.2f}$'       .format(N, N_u),
        '$\sigma_E/E =        {:.2f} \%  $' .format(resolution,)))
    
    
    props = dict(boxstyle='square', facecolor='white', alpha=0.5)
    plt.gca().text(0.05, 0.95, textstr, transform=plt.gca().transAxes, fontsize=14,
                   verticalalignment='top', bbox=props)
    
    frame_data.set_xticklabels([])
    plt.ylabel("Entries")
    plt.ylim(0)
    lims = plt.xlim()
    print(lims)
    
    type(lims)
    frame_res = plt.gcf().add_axes((.1, .1, .8, .2))
    plt.plot    (lims, [0,0], "-g", lw=0.7)  # linia en 00 verde
    plt.errorbar(e, residuals, 1, 0, linestyle='None', fmt='|', c="k")
    plt.ylim(-3.9,3.9)
    plt.xlabel("E (pes)")

    plt.savefig('/Users/neus/current-work/diffusion/energy_resolution/'+name_fig+'.png')