def get_threshold_current(file): """Get the threshold current to initialize AP for a neuron. Input: file: An abf file with voltage under ramp current recorded. Return: A generator containing (cell_ID, trace/sweep, ramp slope(pA/s), threshold current(pA), threshold voltage(mV), spiking_time(s)).""" abf = pyabf.ABF(file) cellid = getCellID(file) dt = abf.dataSecPerPoint start, end = abf.sweepEpochs.p1s[2], abf.sweepEpochs.p2s[2] for sweep in abf.sweepList: abf.setSweep(sweep) dy = np.diff(abf.sweepY[start:end]) dc = np.diff(abf.sweepC[start:end]) dyt = dy / dt dct = dc / dt try: if dyt.max() / dyt.std() < 10: continue # if dv/dt > 5*std(dy/dt), set as threshold point spike_p = np.where(dyt > 5 * dyt.std())[0] th_i = abf.sweepC[spike_p[0] + start] th_v = abf.sweepY[spike_p[0] + start] th_t = abf.sweepX[spike_p[0] + start] yield (cellid, sweep + 1, dct[0], th_i, th_v, th_t) except ValueError: print("Cannot compute rheobase for `{}` trace {}".format( getFileName(file), sweep + 1))
def plot_demo_distribution(self, term, file_id, to_save=""): """Plot a bar plot of AP number vs. sweep number. term: String. Include 'freq', 'amp'. file_id: Interger. the n-th 'freq' file. to_save: file path. If left empty, not to save.""" demoData = self.read_demo_stat(term, file_id) demoData.plot("sweep", "n", kind="bar", legend=False) identifier = getCellID(self.files[term][file_id]) plt.title(identifier) plt.ylabel("AP number") if bool(to_save): to_save_figure(term + " distribution of " + to_save)
def read_demo_stat(self, term, file_ID): """Read statistic data from txt file generated by mini. term: String. Include 'freq', 'amp'. file_ID: demo file order.""" if term in ["freq", "amp"]: filepath = self.files[term][file_ID] dt = pd.read_csv(filepath, sep="\t", skiprows=1) dt.dropna(how="all", inplace=True) dt.rename({"Unnamed: 0": "sweep"}, axis=1, inplace=True) dt.sweep = dt.sweep.str.extract("Group # (\d+)").astype("int64") dt.n = dt.n.astype("int64") dt["CellID"] = getCellID(filepath) dt = dt[np.roll(dt.columns, 1)] return dt
def get_matched_file(self, item1, item2, file_id=0, cell_id=""): """Match pairwise file for 'abf', 'iti', 'event', 'fit', 'freq', 'amp', return actual path instead of a map. Input either file_id in item1 or cell_id. file_id: interger. The n-th file in item1 group. cell_id: string. A cell id what item1_files contains. See `ap_parser.match_file()`""" if not (cell_id): identifier = getCellID(self.files[item1][file_id]) else: identifier = cell_id matched = pd.Series(self.files[item2]) result = matched[matched.str.contains(identifier)].values if len(result) == 0: return "" elif len(result) >= 2: return result.tolist() else: return result[0]
def extract_demo_ap_features(file, features, extract_average=False): """Extract electrophysiological features from an abf file about AP recording. features: list. All features to be extracted. extrace_average: Average the values of the same sweep.""" result = [] visited = [] for f in file: traces = abf2trace(f) cellid = getCellID(f) if cellid in visited: continue cur_result = efel.getFeatureValues(traces, features, raise_warnings=False) cur_result = {cellid: cur_result} visited.append(cellid) if not extract_average: result.append( pd.DataFrame( ((cellid, ind + 1, itemk, itemv[0]) if itemv else (cellid, ind + 1, itemk, None) for cellid, v in cur_result.items() for ind, vv in enumerate(v) for itemk, itemv in vv.items()), columns=["CellID", "trace", "featureName", "featureValue"], )) else: with warnings.catch_warnings(): warnings.simplefilter('ignore') result.append( pd.DataFrame( ((cellid, ind + 1, "mean_" + itemk, itemv.mean()) if isinstance(itemv, np.ndarray) else (cellid, ind + 1, itemk, None) for cellid, v in cur_result.items() for ind, vv in enumerate(v) for itemk, itemv in vv.items()), columns=[ "CellID", "trace", "featureName", "featureValue" ], )) return pd.concat(result, ignore_index=True)
def plot_demo_IF(self, file_id, to_save=""): """Plot instant frequency of each current level for a demo neuron. file_id: the n-th 'event' file. to_save: String. The figure to be saved. Default: empty (not to save).""" IFdemoData = self.get_demo_IF_data(file_id) if IFdemoData is not None: sns_line = sns.lineplot( x="relative_time", y="instantaneous_freq (Hz)", hue="Group", data=IFdemoData[IFdemoData["instantaneous_freq (Hz)"].between( 0, 500, False) & (IFdemoData["Group"] != 0)], estimator=None, ) plt.xlabel("AP onset time (ms)") plt.ylabel("Instantaneous frequency (Hz)") title = getCellID(self.files["event"][file_id]) plt.title(title) plt.show() figIFdemo = sns_line.get_figure() if bool(to_save): figIFdemo.savefig("instantaneous freq of" + title, dpi=600)