def plot_hit(fil_filename, dat_filename, hit_id, bw=None, offset=0): r"""Plot a candidate from a .dat file Args: fil_filename(str): Path to filterbank file to plot dat_filename(str): Path to turbosSETI generated .dat output file of events hit_id(int): ID of hit in the dat file to plot (TopHitNum) offset(float, optional): Offset drift line on plot. Default 0. bw: (Default value = None) Returns: """ # Load hit details dat = find_event.read_dat(dat_filename) hit = dat.iloc[hit_id] f0 = hit['Freq'] if bw is None: bw_mhz = np.abs(hit['FreqStart'] - hit['FreqEnd']) else: bw_mhz = bw * 1e-6 fil = Waterfall(fil_filename, f_start=f0 - bw_mhz / 2, f_stop=f0 + bw_mhz / 2) t_duration = (fil.n_ints_in_file - 1) * fil.header['tsamp'] fil.plot_waterfall() plot_event.overlay_drift(f0, f0, f0, hit['DriftRate'], t_duration, offset)
def grab_parameters(dat_file, GBT_band): """ takes dat file of GBT data and returns frequency parameters used to calculate where the DC spikes will be Arguments ---------- dat_file : str filepath to the .dat file GBT_band : str the band at which the data was collected choose from {"L", "S", "C", "X"} Returns : fch1, foff, nfpc which will be used internally within remove_DC_spike """ tbl = find.read_dat(dat_file) if GBT_band == "L": fch1 = 1926.2695326677515 # LBAND -- this is hardcoded, it would be nice to fix that if GBT_band == "C": fch1 = 8201.66015625 # CBAND "" if GBT_band == "S": fch1 = 2720.80078125 # SBAND "" if GBT_band == "X": fch1 = 11102.05078125 # XBAND "" foff = float(tbl["DELTAF"][0])*1e-6 nfpc=(1500.0/512.0)/abs(foff) num_course_channels = np.max(tbl["CoarseChanNum"]) return fch1, foff, nfpc, num_course_channels
def validate_voyager_hits(filename_dat): """ This checks voyager hits against known values. Known values: # -------------------------- # ID Drift_Rate SNR Unc_Freq Corr_Freq Index freq_start freq_end ... # -------------------------- 001 -0.392226 30.612128 8419.319368 8419.319368 739933 8419.319779 8419.318963 ... 002 -0.373093 245.707984 8419.297028 8419.297028 747929 8419.297439 8419.296623 ... 003 -0.392226 31.220652 8419.274374 8419.274374 756037 8419.274785 8419.273969 ... (from flipped) 003 -0.392226 30.612118 8419.319366 8419.319366 308642 8419.318955 8419.319771 ... 002 -0.373093 245.707905 8419.297025 8419.297025 300646 8419.296614 8419.297430 ... 001 -0.392226 31.220642 8419.274372 8419.274372 292538 8419.273961 8419.274777 ... """ print("\n===== validate_voyager_hits =====") h = find_event.read_dat(filename_dat) print(h) valid_data = [ { 'Freq': 8419.319368, 'FreqStart': 8419.319779, 'FreqEnd': 8419.318963, 'SNR': 30.612128, 'DriftRate': -0.392226, }, { 'Freq': 8419.297028, 'FreqStart': 8419.297439, 'FreqEnd': 8419.296623, 'SNR': 245.707984, 'DriftRate': -0.373093, }, { 'Freq': 8419.274374, 'FreqStart': 8419.274785, 'FreqEnd': 8419.273969, 'SNR': 31.220652, 'DriftRate': -0.392226, } ] atols = {'Freq': 0.000005, 'FreqStart': 0.00001, 'FreqEnd': 0.00001, 'SNR': 0.001, 'DriftRate': 0.02} for vd in valid_data: hmax = h[np.isclose(h['Freq'], vd['Freq'], rtol=0.000001)].iloc[0] for key in vd.keys(): print(key, hmax[key], vd[key]) if key in ('FreqStart', 'FreqEnd'): upper = np.isclose(hmax[key], vd['FreqStart'], atol=atols[key], rtol=0) lower = np.isclose(hmax[key], vd['FreqEnd'], atol=atols[key], rtol=0) assert upper or lower else: assert np.isclose(hmax[key], vd[key], atol=atols[key], rtol=0) return hmax
def grab_parameters(dat_file, GBT_band, use_defaults, h5_fil_path): """ takes dat file of GBT data and returns frequency parameters used to calculate where the DC spikes will be Arguments ---------- dat_file : str filepath to the .dat file GBT_band : str the band at which the data was collected choose from {"L", "S", "C", "X"} use_defaults : bool if True, the program uses the preset, hardcoded fch1 and foff values; if False, fch1 and foff are retrieved from the h5/fil files. h5_fil_path : str the file path to the h5 or fil file corresponding to the given dat file. Program will crash if use_defaults=False and no h5_fil_path is specified. Returns : fch1, foff, nfpc which will be used internally within remove_DC_spike """ tbl = find.read_dat(dat_file) if use_defaults: if GBT_band == "L": fch1 = 1926.2695326677515 # LBAND -- this is hardcoded, it would be nice to fix that if GBT_band == "C": fch1 = 8201.66015625 # CBAND "" if GBT_band == "S": fch1 = 2720.80078125 # SBAND "" if GBT_band == "X": fch1 = 11102.05078125 # XBAND "" foff = float(tbl["DELTAF"][0]) * 1e-6 else: fil = bp.Waterfall(h5_fil_path) fch1 = fil.header['fch1'] foff = fil.header['foff'] #for Karen's files fch1 = float(fch1 - (foff / 2.0)) nfpc = (1500.0 / 512.0) / abs(foff) num_course_channels = np.max(tbl["CoarseChanNum"]) #print('fch1: {0}, foff: {1}'.format(fch1, foff)) return fch1, foff, nfpc, num_course_channels
def validate_voyager_hits(filename_dat): r""" This checks voyager hits against known values. """ print("\n===== validate_voyager_hits =====") df_hits = find_event.read_dat(filename_dat) print(df_hits) valid_data = [ # in unflipped order { # 001 'Freq': 8419.319368, 'FreqStart': 8419.32, 'FreqEnd': 8419.32, 'SNR': 30.612128, }, { # 002 'Freq': 8419.30, 'FreqStart': 8419.30, 'FreqEnd': 8419.30, 'SNR': 245.707984, }, { # 003 'Freq': 8419.274374, 'FreqStart': 8419.27, 'FreqEnd': 8419.27, 'SNR': 31.220652, } ] atols = {'Freq': 0.001, 'FreqStart': 0.001, 'FreqEnd': 0.001, 'SNR': 0.001} for vd in valid_data: hmax = df_hits[np.isclose(df_hits['Freq'], vd['Freq'], rtol=0.000001)].iloc[0] for key in vd.keys(): #print('validate_voyager_hits: key, hmax[key], vd[key]: ', key, hmax[key], vd[key]) if key in ('FreqStart', 'FreqEnd'): upper = np.isclose(hmax[key], vd['FreqStart'], atol=atols[key]) lower = np.isclose(hmax[key], vd['FreqEnd'], atol=atols[key]) if not (upper and lower): raise ValueError( 'validate_voyager_hits: upper or lower: hmax[key]={}, vd[FreqStart]={}, vd[FreqEnd]={}' .format(hmax[key], vd['FreqStart'], vd['FreqEnd'])) else: if not np.isclose(hmax[key], vd[key], atol=atols[key]): raise ValueError( 'validate_voyager_hits: other: key={}, hmax[key]={}, vd[key]={}' .format(key, hmax[key], vd[key])) print('\nvalidate_voyager_hits: SUCCESS\n')
def calculate_hist(dat_file, GBT_band, bin_width=1, tbl=None): """ calculates a histogram of the number of hits for a single .dat file Arguments ---------- dat_file : str filepath to the .dat file GBT_band : str the band at which the data was collected choose from {"L", "S", "C", "X"} bin_width : float width of the hisrogram bins in units of MHz The default is 1 Mhz tbl : pandas.core.frame.DataFrame Alternate way of providing contents of a dat file Returns -------- hist : numpy.ndarray the count of hits in each bin bin_edges : numpy.ndarray the edge values of each bin. Has length Nbins+1 """ #read the file into a pandas dataframe if type(tbl) != pandas.core.frame.DataFrame: tbl = find.read_dat(dat_file) #make the bins for the histogram # band boundaries as listed in Traas 2021 if GBT_band == "L": min_freq = 1100 max_freq = 1900 if GBT_band == "S": min_freq = 1800 max_freq = 2800 if GBT_band == "C": min_freq = 4000 max_freq = 7800 if GBT_band == "X": min_freq = 7800 max_freq = 11200 bins = np.linspace(min_freq, max_freq, int((max_freq - min_freq) / bin_width), endpoint=True) hist, bin_edges = np.histogram(tbl["Freq"], bins=bins) return hist, bin_edges
def plot_hits(filename_fil, filename_dat): r""" Plot the hits in a .dat file. """ print("\n===== plot_hits =====") table = find_event.read_dat(filename_dat) print(table) plt.figure(figsize=(10, 8)) N_hit = len(table) if N_hit > 10: print("Warning: More than 10 hits found. Only plotting first 10") N_hit = 10 for ii in range(N_hit): plt.subplot(N_hit, 1, ii + 1) plot_hit(filename_fil, filename_dat, ii) plt.tight_layout() plt.savefig(filename_dat.replace('.dat', '.png'))