copying to personal repo

This commit is contained in:
Alan
2022-06-19 13:45:53 -05:00
commit bf2ffa7315
287 changed files with 54032 additions and 0 deletions

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,96 @@
# coding: utf-8
# In[1]:
import os
import sys
import pyqtgraph as pg
import numpy as np
# In[7]:
dir_path = os.path.abspath("")
win = pg.GraphicsWindow()
win.setBackground("w")
p1 = win.addPlot(
title="Pauser PSTH",
row=0,
col=0,
labels={"bottom": "T (ms)", "left": "# of spikes"},
)
p2 = win.addPlot(
title="Buildup PSTH",
row=1,
col=0,
labels={"bottom": "T (ms)", "left": "# of spikes"},
)
p3 = win.addPlot(
title="Wide Chopper PSTH",
row=2,
col=0,
labels={"bottom": "T (ms)", "left": "# of spikes"},
)
# In[ ]:
bins = np.arange(0, 80, 0.5)
PB_spike_data = []
with open("Ad081098_065_PauserBuildup_psth.txt", "r+") as df:
for x in df:
x = x.strip("\n").strip()
x = float(x) * 1e-3
if x:
PB_spike_data.append(x)
histogram, binedges = np.histogram(PB_spike_data, bins)
p1.plot(
binedges,
histogram,
stepMode=True,
fillBrush=(0, 0, 0, 255),
brush=pg.mkBrush("k"),
fillLevel=0,
)
B_spike_data = []
with open("Ad041599_062_Buildup_psth.txt", "r+") as df:
for x in df:
x = x.strip("\n").strip()
x = float(x) * 1e-3
if x:
B_spike_data.append(x)
histogram, binedges = np.histogram(B_spike_data, bins)
p2.plot(
binedges,
histogram,
stepMode=True,
fillBrush=(0, 0, 0, 255),
brush=pg.mkBrush("k"),
fillLevel=0,
)
C_spike_data = []
with open("Ad081998_199_WideChopper_psth.txt", "r+") as df:
for x in df:
x = x.strip("\n").strip()
x = float(x) * 1e-3
if x:
C_spike_data.append(x)
histogram, binedges = np.histogram(C_spike_data, bins)
p3.plot(
binedges,
histogram,
stepMode=True,
fillBrush=(0, 0, 0, 255),
brush=pg.mkBrush("k"),
fillLevel=0,
)
# In[ ]:
win.show()
print("finished")
if sys.flags.interactive == 0:
pg.QtGui.QApplication.exec_()

View File

@@ -0,0 +1,451 @@
"""
Layout:
if __name__==__main__ handles cmd args, instantiates test, runs it, displays results
run_trial(): defines a model and then runs the test using preset params in hoc and return the info to the class
SGCInputTest:
__init__ : defines many static variables
run(): calls delivers information to the run_trial() function and the recieved information of a single run
back and stores it as an exstensible list in the class
show(): displays graphs depending on the graph options selected below it and displayed in a printout
"""
import argparse
import numpy as np
import pyqtgraph as pg
from neuron import h
from cnmodel.protocols import Protocol
from cnmodel import cells
from cnmodel.util import sound
from cnmodel.util import custom_init
import cnmodel.util.pynrnutilities as PU
from cnmodel import data
try:
from tqdm import trange
except ImportError:
raise ImportError("Please 'pip install tqdm' to allow for progress bar")
species = "rat" # tables for other species do not yet exist
def run_trial(cell, info):
"""
info is a dict
"""
assert cell == "pyramidal"
post_cell = cells.Pyramidal.create(species=species)
inhib_cell = cells.Tuberculoventral.create()
inhib_cell2 = cells.Tuberculoventral.create()
# dstell = cells.DStellate.create()
pre_cells = []
synapses = []
inhib_synapses = []
for nsgc in range(48):
# attach to pyramidal cell
pre_cells.append(cells.DummySGC(cf=info["cf"], sr=info["sr"]))
synapses.append(pre_cells[-1].connect(post_cell, type=info["synapse_type"]))
pre_cells[-1].set_sound_stim(
info["stim"], seed=info["seed"] + nsgc, simulator=info["simulator"]
)
synapses[
-1
].terminal.relsite.Dep_Flag = False # no depression in these simulations
for nsgc in range(16):
pre_cells.append(cells.DummySGC(cf=info["cf"], sr=info["sr"]))
inhib_synapses.append(
pre_cells[-1].connect(inhib_cell, type=info["synapse_type"])
)
inhib_synapses.append(
pre_cells[-1].connect(inhib_cell2, type=info["synapse_type"])
)
pre_cells[-1].set_sound_stim(
info["stim"], seed=info["seed"] + nsgc + 48, simulator=info["simulator"]
)
synapses[
-1
].terminal.relsite.Dep_Flag = False # no depression in these simulations
# for nsgc in range(20):
# pre_cells.append(cells.DummySGC(cf=info['cf'], sr=info['sr']))
# inhib_synapses.append(pre_cells[-1].connect(dstell, type=info['synapse_type']))
# pre_cells[-1].set_sound_stim(info['stim'], seed=info['seed'] + nsgc + 16 + 48, simulator=info['simulator'])
# synapses[-1].terminal.relsite.Dep_Flag = False # no depression in these simulations
for _ in range(21):
inhib_synapses.append(inhib_cell.connect(post_cell, type="simple"))
inhib_synapses.append(inhib_cell2.connect(post_cell, type="simple"))
# for _ in range(15):
# inhib_synapses.append(inhib_cell.connect(dstell, type='simple'))
Vm = h.Vector()
Vm.record(post_cell.soma(0.5)._ref_v)
Vmtb = h.Vector()
Vmtb.record(inhib_cell.soma(0.5)._ref_v)
rtime = h.Vector()
rtime.record(h._ref_t)
h.tstop = 1e3 * info["run_duration"] # duration of a run
h.celsius = info["temp"]
h.dt = info["dt"]
post_cell.cell_initialize()
info["init"]()
h.t = 0.0
h.run()
# package data
pre_cells_data = [x._spiketrain for x in pre_cells]
Vm_list = np.array(Vm)
Vmtb_list = np.array(Vmtb)
time_list = np.array(rtime)
# clean up
del (
pre_cells,
synapses,
inhib_cell,
inhib_synapses,
Vm,
Vmtb,
post_cell,
inhib_cell2,
info,
)
return {
"time": time_list,
"vm": Vm_list,
"pre_cells": pre_cells_data,
"vmtb": Vmtb_list,
}
class SGCTestPSTH(Protocol):
"""
Tests a Single cell with input recieved from the SGC
__init__: almost all parameters can be modified
run(): simply loops over the run_trial() function and stores the results just
show(): constructs the graphs using other functions
"""
def __init__(
self,
temp=34.0,
seed=2918,
nrep=10,
stimulus="tone",
simulator="cochlea",
n_sgc=12,
debug=True,
cell="pyramidal",
):
"""
:param temp: (float) must be at 34 for default pyramidal cells
:param dt: (float) determine hoc resolution
:param seed: (int) contributes to randomization, needs to be changed to see different results (reduce this
number if you keep getting a timeout error
:param nrep: (int) number of presentations !!must be changed in the __name__ function if not calling from cmd line!!
:param stimulus: (str) must be 'tone'
:param simulator: (str) currently using cochlea instead of matlab
:param n_sgc:(int) This is the number of SGC fibers that connect to the post synaptic cell
:param debug: (bool) controls most of the terminal printouts is on by default
:param cell: (str) cell type !!must be changed in the __name__ function if not calling from cmd line!!
"""
super().__init__()
assert stimulus == "tone"
assert cell in [
"bushy",
"tstellate",
"octopus",
"dstellate",
"tuberculoventral",
"pyramidal",
]
self.debug = debug
self.nrep = nrep
self.stimulus = stimulus
self.run_duration = 0.30 # in seconds
self.pip_duration = 0.05 # in seconds
self.pip_start = [0.1] # in seconds
self.Fs = 100e3 # in Hz
self.f0 = 13000.0 # stimulus in Hz
self.cf = 13000.0 # SGCs in Hz
self.fMod = 100.0 # mod freq, Hz
self.dMod = 0.0 # % mod depth, Hz
self.dbspl = 40.0
self.simulator = simulator
self.sr = 2 # set SR group
self.seed = seed
self.temp = temp
self.dt = 0.025
self.cell = cell
self.synapse_type = "multisite"
if self.stimulus == "tone":
self.stim = sound.TonePip(
rate=self.Fs,
duration=self.run_duration,
f0=self.f0,
dbspl=self.dbspl,
ramp_duration=5e-3,
pip_duration=self.pip_duration,
pip_start=self.pip_start,
)
if not n_sgc:
n_sgc = data.get(
"convergence", species="mouse", post_type=self.cell, pre_type="sgc"
)[0]
self.n_sgc = int(np.round(n_sgc))
# convert nS to uS for NEURON
self.vms = [None for n in range(self.nrep)]
self.vmtbs = [None for n in range(self.nrep)]
self.synapses = [None for n in range(self.nrep)]
self.pre_cells = [None for n in range(self.nrep)]
self.time = [None for n in range(self.nrep)]
# debug function reports a print out of various information about the run
if self.debug:
print("SGCInputTest Created")
print()
print("Test parameters")
print("#" * 70)
print(f"Running test of {cell} cell synapse with Simulated SGC fibers")
print()
print(f"Run Conditions: Run Time: {self.run_duration}s,")
print(f" Run Temp: {self.temp} ")
print(f" Sgc Connections {n_sgc}")
print(f" Number of Presentations: {nrep}")
print()
print(f"Stimulus Conditions: Type: {stimulus}")
print(f" Stim Duration: {self.pip_duration}s")
print(f" Characteristic F: {self.cf}hz")
print(f" Stim Start:{str(self.pip_start)}s")
def run(self):
super().run()
info = {
"n_sgc": self.n_sgc,
"stim": self.stim,
"simulator": self.simulator,
"cf": self.cf,
"sr": self.sr,
"seed": self.seed,
"run_duration": self.run_duration,
"synapse_type": self.synapse_type,
"temp": self.temp,
"dt": self.dt,
"init": custom_init,
}
for nr in trange(self.nrep):
info["seed"] = self.seed + self.n_sgc + (nr * (48 + 16 + 20))
res = run_trial(self.cell, info)
# res contains: {'time': time, 'vm': list(Vm), 'pre_cells': pre_cells._spiketrain,'vmtb': list(Vmtb)}
self.pre_cells[nr] = res["pre_cells"]
self.time[nr] = res["time"]
self.vms[nr] = res["vm"]
self.vmtbs[nr] = res["vmtb"]
def show(self):
"""
Creates a single page graph that contains all of the graphs based on the graphical functions in the class
"""
self.win = pg.GraphicsWindow()
self.win.setBackground("w")
p1 = self.stimulus_graph()
p2 = self.an_spike_graph()
p3 = self.pyram_spike_graph()
p4 = self.voltage_graph()
p5 = self.tb_cell_spike_graph()
p6 = (
self.an_psth_graph()
) # requires that an_spikes_graph() has been called before
p7 = (
self.cell_psth_graph()
) # requires that cell_spikes_graph() has been called before
# links x axis
p1.setXLink(p1)
p2.setXLink(p1)
p3.setXLink(p1)
p4.setXLink(p1)
p5.setXLink(p1)
p6.setXLink(p1)
p7.setXLink(p1)
self.win.show()
if self.debug:
print("finished")
############# Graph options to be included in the show() method ###################
def stimulus_graph(self):
p1 = self.win.addPlot(
title="Stimulus", row=0, col=0, labels={"bottom": "T (ms)", "left": "V"}
)
p1.plot(self.stim.time * 1000, self.stim.sound, pen=pg.mkPen("k", width=0.75))
return p1
def an_spike_graph(self):
p2 = self.win.addPlot(
title="AN spikes",
row=1,
col=0,
labels={"bottom": "T (ms)", "left": "AN spikes (first trial)"},
)
self.all_xan = []
for nr in range(self.nrep):
xan = []
yan = []
for k in range(len(self.pre_cells[nr])):
r = self.pre_cells[nr][k]
xan.extend(r)
self.all_xan.extend(r)
yr = k + np.zeros_like(r) + 0.2
yan.extend(yr)
c = pg.PlotCurveItem()
xp = np.repeat(np.array(xan), 2)
yp = np.repeat(np.array(yan), 2)
yp[1::2] = yp[::2] + 0.6
c.setData(
xp.flatten(),
yp.flatten(),
connect="pairs",
width=1.0,
pen=pg.mkPen("k", width=1.5),
)
p2.addItem(c)
return p2
def pyram_spike_graph(self):
p3 = self.win.addPlot(
title="Pyramidal Spikes",
row=2,
col=0,
labels={"bottom": "T (ms)", "left": "Trial #"},
)
xcn = []
ycn = []
for k in range(self.nrep):
bspk = PU.findspikes(self.time[k], self.vms[k], -35.0)
xcn.extend(bspk)
yr = k + np.zeros_like(bspk) + 0.2
ycn.extend(yr)
d = pg.PlotCurveItem()
xp = np.repeat(np.array(xcn), 2)
yp = np.repeat(np.array(ycn), 2)
yp[1::2] = yp[::2] + 0.6
d.setData(
xp.flatten(), yp.flatten(), connect="pairs", pen=pg.mkPen("k", width=1.5)
)
self.xcn = xcn
self.ycn = ycn
p3.addItem(d)
return p3
def voltage_graph(self):
p4 = self.win.addPlot(
title="%s Vm" % self.cell,
row=0,
col=1,
labels={"bottom": "T (ms)", "left": "Vm (mV)"},
)
if self.nrep > 3:
display = 3
else:
display = self.nrep
for nr in range(display):
p4.plot(
self.time[nr],
self.vms[nr],
pen=pg.mkPen(pg.intColor(nr, self.nrep), hues=self.nrep, width=1.0),
)
return p4
def tb_cell_spike_graph(self):
p5 = self.win.addPlot(
title="Tuberculoventral Spikes",
row=3,
col=0,
labels={"bottom": "T (ms)", "left": "Trial #"},
)
xtcn = []
ytcn = []
for k in range(self.nrep):
bspk = PU.findspikes(self.time[k], self.vmtbs[k], -35.0)
xtcn.extend(bspk)
yr = k + np.zeros_like(bspk) + 0.2
ytcn.extend(yr)
d = pg.PlotCurveItem()
xp = np.repeat(np.array(xtcn), 2)
yp = np.repeat(np.array(ytcn), 2)
yp[1::2] = yp[::2] + 0.6
d.setData(
xp.flatten(), yp.flatten(), connect="pairs", pen=pg.mkPen("k", width=1.5)
)
p5.addItem(d)
return p5
def an_psth_graph(self):
p6 = self.win.addPlot(
title="AN PSTH",
row=1,
col=1,
labels={"bottom": "T (ms)", "left": "Sp/ms/trial"},
)
bins = np.arange(50, 200, 1)
(hist, binedges) = np.histogram(self.all_xan, bins)
curve6 = p6.plot(
binedges,
hist,
stepMode=True,
fillBrush=(0, 0, 0, 255),
brush=pg.mkBrush("k"),
fillLevel=0,
)
return p6
def cell_psth_graph(self):
p7 = self.win.addPlot(
title="Pyramidal PSTH",
row=2,
col=1,
labels={"bottom": "T (ms)", "left": "Sp/ms/trial"},
)
bins = np.arange(50, 200, 1)
(hist, binedges) = np.histogram(self.xcn, bins)
curve7 = p7.plot(
binedges,
hist,
stepMode=True,
fillBrush=(0, 0, 0, 255),
brush=pg.mkBrush("k"),
fillLevel=0,
)
return p7
if __name__ == "__main__":
parser = argparse.ArgumentParser(
description="Compute AN only PSTH in postsynaptic cell"
)
parser.add_argument(
"-n",
"--nrep",
type=int,
dest="nrep",
default=10,
help="Set number of repetitions",
)
args = parser.parse_args()
nrep = args.nrep
prot = SGCTestPSTH(nrep=50)
prot.run()
prot.show()
import sys
if sys.flags.interactive == 0:
pg.QtGui.QApplication.exec_()

View File

@@ -0,0 +1,412 @@
"""
Layout:
if __name__==__main__ handles cmd args, instantiates test, runs it, displays results
run_trial(): defines a model and then runs the test using preset params in hoc and return the info to the class
SGCInputTest:
__init__ : defines many static variables
run(): calls delivers information to the run_trial() function and the recieved information of a single run
back and stores it as an exstensible list in the class
show(): displays graphs depending on the graph options selected below it and displayed in a printout
"""
import argparse
import numpy as np
import pyqtgraph as pg
from neuron import h
from cnmodel.protocols import Protocol
from cnmodel import cells
from cnmodel.util import sound
from cnmodel.util import custom_init
import cnmodel.util.pynrnutilities as PU
from cnmodel import data
try:
from tqdm import trange
except ImportError as err:
raise ImportError("Please 'pip install tqdm' to allow for progress bar")
species = "rat" # tables for other species do not yet exist
def run_trial(cell, info):
"""
info is a dict
"""
if cell == "bushy":
post_cell = cells.Bushy.create(species=species)
elif cell == "tstellate":
post_cell = cells.TStellate.create(species=species)
elif cell == "octopus":
post_cell = cells.Octopus.create(species=species)
elif cell == "dstellate":
post_cell = cells.DStellate.create(species=species)
elif cell == "tuberculoventral":
post_cell = cells.DStellate.create(species=species)
elif cell == "pyramidal":
post_cell = cells.Pyramidal.create(species=species)
else:
raise ValueError("cell %s is not yet implemented for PSTH testing" % cell)
pre_cells = []
synapses = []
for nsgc, sgc in enumerate(range(info["n_sgc"])):
pre_cells.append(cells.DummySGC(cf=info["cf"], sr=info["sr"]))
synapses.append(pre_cells[-1].connect(post_cell, type=info["synapse_type"]))
synapses[
-1
].terminal.relsite.Dep_Flag = False # no depression in these simulations
pre_cells[-1].set_sound_stim(
info["stim"], seed=info["seed"] + nsgc, simulator=info["simulator"]
)
# stim = insert_current_clamp(post_cell.soma)
Vm = h.Vector()
Vm.record(post_cell.soma(0.5)._ref_v)
rtime = h.Vector()
rtime.record(h._ref_t)
h.tstop = 1e3 * info["run_duration"] # duration of a run
h.celsius = info["temp"]
h.dt = info["dt"]
post_cell.cell_initialize()
info["init"](v_init=-60)
h.t = 0.0
h.run()
pre_cells_data = [x._spiketrain for x in pre_cells]
return {"time": np.array(rtime), "vm": list(Vm), "pre_cells": pre_cells_data}
# stim = insert_current_clamp(post_cell.soma)
def insert_current_clamp(sec):
"""
:param sec: to attach too
dur: ms
amp: nA
delay: ms
:return: stim needs to be put in a variable to stay alive
"""
stim = h.IClamp(0.5, sec=sec)
stim.dur = 90
stim.amp = -0.2
stim.delay = 2
return stim
class SGCTestPSTH(Protocol):
"""
Tests a Single cell with input recieved from the SGC
__init__: almost all parameters can be modified
run(): simply loops over the run_trial() function and stores the results just
show(): constructs the graphs using other functions
"""
def __init__(
self,
temp=34.0,
seed=5908035,
nrep=10,
stimulus="tone",
simulator="cochlea",
n_sgc=12,
debug=True,
cell="bushy",
):
"""
:param temp: (float) must be at 34 for default pyramidal cells
:param dt: (float) determine hoc resolution
:param seed: (int) contributes to randomization, needs to be changed to see different results (reduce this
number if you keep getting a timeout error
:param nrep: (int) number of presentations !!must be changed in the __name__ function if not calling from cmd line!!
:param stimulus: (str) must be 'tone'
:param simulator: (str) currently using cochlea instead of matlab
:param n_sgc:(int) This is the number of SGC fibers that connect to the post synaptic cell
:param debug: (bool) controls most of the terminal printouts is on by default
:param cell: (str) cell type !!must be changed in the __name__ function if not calling from cmd line!!
"""
super().__init__()
assert stimulus == "tone"
assert cell in [
"bushy",
"tstellate",
"octopus",
"dstellate",
"tuberculoventral",
"pyramidal",
]
self.debug = debug
self.nrep = nrep
self.stimulus = stimulus
self.run_duration = 0.30 # in seconds
self.pip_duration = 0.05 # in seconds
self.pip_start = [0.1] # in seconds
self.Fs = 100e3 # in Hz
self.f0 = 13000.0 # stimulus in Hz
self.cf = 13000.0 # SGCs in Hz
self.fMod = 100.0 # mod freq, Hz
self.dMod = 0.0 # % mod depth, Hz
self.dbspl = 55.0
self.simulator = simulator
self.sr = 2 # set SR group
self.seed = seed
self.temp = temp
self.dt = 0.025
self.cell = cell
self.synapse_type = "multisite"
if self.stimulus == "tone":
self.stim = sound.TonePip(
rate=self.Fs,
duration=self.run_duration,
f0=self.f0,
dbspl=self.dbspl,
ramp_duration=2.5e-3,
pip_duration=self.pip_duration,
pip_start=self.pip_start,
)
if not n_sgc:
n_sgc = data.get(
"convergence", species="mouse", post_type=self.cell, pre_type="sgc"
)[0]
self.n_sgc = int(np.round(n_sgc))
# convert nS to uS for NEURON
self.vms = [None for n in range(self.nrep)]
self.synapses = [None for n in range(self.nrep)]
self.pre_cells = [None for n in range(self.nrep)]
self.time = [None for n in range(self.nrep)]
# debug function reports a print out of various information about the run
if self.debug:
print("SGCInputTest Created")
print()
print("Test parameters")
print("#" * 70)
print(f"Running test of {cell} cell synapse with Simulated SGC fibers")
print()
print(f"Run Conditions: Run Time: {self.run_duration}s,")
print(f" Run Temp: {self.temp} ")
print(f" Sgc Connections {n_sgc}")
print(f" Number of Presentations: {nrep}")
print()
print(f"Stimulus Conditions: Type: {stimulus}")
print(f" Stim Duration: {self.pip_duration}s")
print(f" Characteristic F: {self.cf}hz")
print(f" Stim Start:{str(self.pip_start)}s")
def run(self):
super().run()
info = {
"n_sgc": self.n_sgc,
"stim": self.stim,
"simulator": self.simulator,
"cf": self.cf,
"sr": self.sr,
"seed": self.seed,
"run_duration": self.run_duration,
"synapse_type": self.synapse_type,
"temp": self.temp,
"dt": self.dt,
"init": custom_init,
}
for nr in trange(self.nrep):
info["seed"] = self.seed + self.n_sgc + nr + 3
res = run_trial(self.cell, info)
# res contains: {'time': time, 'vm': list(Vm), 'pre_cells': pre_cells._spiketrain,}
self.pre_cells[nr] = res["pre_cells"]
self.time[nr] = res["time"]
self.vms[nr] = res["vm"]
def show(self):
"""
Creates a single page graph that contains all of the graphs based on the graphical functions in the class
"""
self.win = pg.GraphicsWindow()
self.win.setBackground("w")
p1 = self.stimulus_graph()
p2 = self.an_spikes_graph()
p3 = self.cell_spikes_graph()
p4 = self.voltage_graph()
p6 = (
self.an_psth_graph()
) # requires that an_spikes_graph() has been called before
p7 = (
self.cell_psth_graph()
) # requires that cell_spikes_graph() has been called before
# links x axis
p1.setXLink(p1)
p2.setXLink(p1)
p3.setXLink(p1)
p4.setXLink(p1)
self.win.show()
if self.debug:
print("finished")
############# Graph options to be included in the show() method ###################
def stimulus_graph(self):
p1 = self.win.addPlot(
title="Single Tone Stimulus", row=0, col=0, labels={"bottom": "T (ms)"}
)
p1.plot(self.stim.time * 1000, self.stim.sound, pen=pg.mkPen("k", width=0.75))
return p1
def an_spikes_graph(self):
p2 = self.win.addPlot(
title="AN spikes",
row=1,
col=0,
labels={"bottom": "T (ms)", "left": "AN spikes (first trial)"},
)
self.all_xan = []
for nr in range(self.nrep):
xan = []
yan = []
for k in range(len(self.pre_cells[nr])):
r = self.pre_cells[nr][k]
xan.extend(r)
self.all_xan.extend(r)
yr = k + np.zeros_like(r) + 0.2
yan.extend(yr)
c = pg.PlotCurveItem()
xp = np.repeat(np.array(xan), 2)
yp = np.repeat(np.array(yan), 2)
yp[1::2] = yp[::2] + 0.6
c.setData(
xp.flatten(),
yp.flatten(),
connect="pairs",
width=1.0,
pen=pg.mkPen("k", width=1.5),
)
p2.addItem(c)
return p2
def cell_spikes_graph(self):
p3 = self.win.addPlot(
title="Pyramidal Cell Spikes",
row=2,
col=0,
labels={"bottom": "T (ms)", "left": "Trial #"},
)
xcn = []
ycn = []
for k in range(self.nrep):
bspk = PU.findspikes(self.time[k], self.vms[k], -35.0)
xcn.extend(bspk)
yr = k + np.zeros_like(bspk) + 0.2
ycn.extend(yr)
d = pg.PlotCurveItem()
xp = np.repeat(np.array(xcn), 2)
yp = np.repeat(np.array(ycn), 2)
yp[1::2] = yp[::2] + 0.6
d.setData(
xp.flatten(), yp.flatten(), connect="pairs", pen=pg.mkPen("k", width=1.5)
)
self.xcn = xcn
self.ycn = ycn
p3.addItem(d)
return p3
def voltage_graph(self):
p4 = self.win.addPlot(
title="Pyramidal Vm",
row=0,
col=1,
labels={"bottom": "T (ms)", "left": "Vm (mV)"},
)
if self.nrep > 5:
display = 3
else:
display = self.nrep
for nr in range(display):
p4.plot(
self.time[nr],
self.vms[nr],
pen=pg.mkPen(pg.intColor(nr, self.nrep), hues=self.nrep, width=1.0),
)
return p4
def an_psth_graph(self):
p6 = self.win.addPlot(
title="AN PSTH",
row=1,
col=1,
labels={"bottom": "T (ms)", "left": "# of Spikes(0.75ms"},
)
bins = np.arange(60, 200, 0.5)
(hist, binedges) = np.histogram(self.all_xan, bins)
curve6 = p6.plot(
binedges,
hist,
stepMode=True,
fillBrush=(0, 0, 0, 255),
brush=pg.mkBrush("k"),
fillLevel=0,
)
return p6
def cell_psth_graph(self):
p7 = self.win.addPlot(
title="Pyramidal PSTH",
row=2,
col=1,
labels={"bottom": "T (ms)", "left": "# of Spikes(0.75ms)"},
)
bins = np.arange(60, 200, 0.5)
(hist, binedges) = np.histogram(self.xcn, bins)
curve7 = p7.plot(
binedges,
hist,
stepMode=True,
fillBrush=(0, 0, 0, 255),
brush=pg.mkBrush("k"),
fillLevel=0,
)
return p7
if __name__ == "__main__":
parser = argparse.ArgumentParser(
description="Compute AN only PSTH in postsynaptic cell"
)
parser.add_argument(
type=str,
dest="cell",
default="pyramidal",
choices=[
"bushy",
"tstellate",
"dstellate",
"octopus",
"tuberculoventral",
"pyramidal",
],
help="Select target cell",
)
parser.add_argument(
"-n",
"--nrep",
type=int,
dest="nrep",
default=1,
help="Set number of repetitions",
)
args = parser.parse_args()
cell = args.cell
nrep = args.nrep
prot = SGCTestPSTH(nrep=100, cell=cell)
prot.run()
prot.show()
import sys
if sys.flags.interactive == 0:
pg.QtGui.QApplication.exec_()

View File

@@ -0,0 +1,397 @@
"""
The Assumptions of this cell are modified to the test_sgc_input_PSTH.py but should be identical in function
synapse type = simple
synapse type = single
species = mouse
sgc = dummy SGC lacks cell body
cell connection = pyramidal
"""
import sys
import numpy as np
import pyqtgraph as pg
from neuron import h
from cnmodel.protocols import Protocol
from cnmodel import cells
from cnmodel.util import sound
from cnmodel.util import custom_init
import cnmodel.util.pynrnutilities as PU
from cnmodel import data
synapseType = "simple" # no other options exist
species = "mouse" # tables for other species do not yet exist
def main():
prot = SGCInputTestPSTH(seed=1233451898)
prot.run()
prot.show()
if sys.flags.interactive == 0:
pg.QtGui.QApplication.exec_()
class SGCInputTestPSTH(Protocol):
def __init__(self, temp=34.0, dt=0.025, seed=575982035):
"""
:param temp: Celcius
:param dt: resolution in ms
:param seed: seed should be generated randomly
Pre-determined variables that can be changed by editing the value next to them
AMPA_gmax and n_sgc = loaded from data that is kept in cnmodel/data dir
Defines a single tone parameters with which to test the neuron complex
"""
# super only defines reset function
super(SGCInputTestPSTH, self).__init__()
#
self.temp = temp
self.dt = dt
self.seed = seed
self.simulator = "cochlea"
# predetermined variables
self.cell = "pyramidal"
self.nrep = 50 # number of repetitions
self.stimulus = "tone"
self.Fs = 100e3 # in Hz
self.f0 = 4000.0 # stimulus in Hz
self.cf = 4000.0 # SGCs in Hz
self.fMod = 100.0 # mod freq, Hz
self.dMod = 0.0 # % mod depth, Hz
self.dbspl = 50.0
self.sr = 2 # set SR group
# variables loaded from data
AMPA_gmax, n_sgc = self.load_variables_from_data()
self.n_sgc = int(np.round(n_sgc))
# value needed for simple synapses
self.AMPA_gmax = AMPA_gmax
# the stimulation delivered is a Tone
self.run_duration = 0.20 # in seconds
self.pip_duration = 0.05 # in seconds
self.pip_start = [0.1] # in seconds
self.f0 = 4000.0
self.cf = 4000.0
self.stim = sound.TonePip(
rate=self.Fs,
duration=self.run_duration,
f0=self.f0,
dbspl=self.dbspl,
ramp_duration=2.5e-3,
pip_duration=self.pip_duration,
pip_start=self.pip_start,
)
# creates empty lists that will contain the results of each rep
self.vms = [None for n in range(self.nrep)]
self.synapses = [None for n in range(self.nrep)]
self.xmtrs = [None for n in range(self.nrep)]
self.pre_cells = [None for n in range(self.nrep)]
self.time = [None for n in range(self.nrep)]
def load_variables_from_data(self):
AMPA_gmax = (
data.get(
"sgc_synapse", species=species, post_type=self.cell, field="AMPA_gmax"
)[0]
/ 1e3
)
n_sgc = data.get(
"convergence", species=species, post_type=self.cell, pre_type="sgc"
)[0]
print(n_sgc)
return AMPA_gmax, n_sgc
def check_assertations(self):
assert self.cell in [
"bushy",
"tstellate",
"octopus",
"dstellate",
"tuberculoventral",
"pyramidal",
]
assert self.stimulus == "tone" # cases available
assert synapseType == "simple"
def run(self):
self.check_assertations()
# info based on the parameters set in the __init__ statement
info = {
"n_sgc": self.n_sgc,
"gmax": self.AMPA_gmax,
"stim": self.stim,
"simulator": self.simulator,
"cf": self.cf,
"sr": self.sr,
"seed": self.seed,
"run_duration": self.run_duration,
"temp": self.temp,
"dt": self.dt,
"init": custom_init,
}
# run number of trials based on nrep defined in __init__ statement
for nr in range(self.nrep):
info["seed"] = self.seed + 3 * self.n_sgc * nr
res = run_trial(info)
# res contains: {'time': time, 'vm': Vm, 'xmtr': xmtr, 'pre_cells': pre_cells, 'post_cell': post_cell}
# unpacks the res dict returned from the run_trial() into refrenceable variables
self.pre_cells[nr] = res["pre_cells"]
self.time[nr] = res["time"]
self.xmtr = {k: v.to_python() for k, v in res["xmtr"].items()}
self.vms[nr] = res["vm"]
self.synapses[nr] = res["synapses"]
self.xmtrs[nr] = self.xmtr
def show(self):
"""
Creates a single page graph that contains all of the graphs based on the graphical functions in the class
"""
self.win = pg.GraphicsWindow()
self.win.setBackground("w")
p1 = self.stimulus_graph()
p2 = self.an_spikes_graph()
p3 = self.cell_spikes_graph()
p4 = self.voltage_graph()
p5 = self.xmtr_graph()
p6 = (
self.an_psth_graph()
) # requires that an_spikes_graph() has been called before
p7 = (
self.cell_psth_graph()
) # requires that cell_spikes_graph() has been called before
# links x axis
p1.setXLink(p1)
p2.setXLink(p1)
p3.setXLink(p1)
p4.setXLink(p1)
p5.setXLink(p1)
self.win.show()
############# Graph options to be included in the show() method ###################
def stimulus_graph(self):
p1 = self.win.addPlot(
title="Stimulus", row=0, col=0, labels={"bottom": "T (ms)", "left": "V"}
)
p1.plot(
self.stim.time * 1000, self.stim.sound, pen=pg.mkPen("k", width=0.75)
)
return p1
def an_spikes_graph(self):
p2 = self.win.addPlot(
title="AN spikes",
row=1,
col=0,
labels={"bottom": "T (ms)", "left": "AN spikes (first trial)"},
)
for nr in range(self.nrep):
xan = []
yan = []
for k in range(len(self.pre_cells[nr])):
r = self.pre_cells[nr][k]._spiketrain
xan.extend(r)
yr = k + np.zeros_like(r) + 0.2
yan.extend(yr)
c = pg.PlotCurveItem()
xp = np.repeat(np.array(xan), 2)
yp = np.repeat(np.array(yan), 2)
yp[1::2] = yp[::2] + 0.6
c.setData(
xp.flatten(),
yp.flatten(),
connect="pairs",
pen=pg.mkPen(pg.intColor(nr, self.nrep), hues=self.nrep, width=1.0),
)
self.xan = xan
self.yan = yan
p2.addItem(c)
return p2
def cell_spikes_graph(self):
p3 = self.win.addPlot(
title="%s Spikes" % self.cell,
row=2,
col=0,
labels={"bottom": "T (ms)", "left": "Trial #"},
)
xcn = []
ycn = []
xspks = []
for k in range(self.nrep):
bspk = PU.findspikes(self.time[k], self.vms[k], -35.0)
xcn.extend(bspk)
yr = k + np.zeros_like(bspk) + 0.2
ycn.extend(yr)
d = pg.PlotCurveItem()
xp = np.repeat(np.array(xcn), 2)
yp = np.repeat(np.array(ycn), 2)
yp[1::2] = yp[::2] + 0.6
d.setData(
xp.flatten(),
yp.flatten(),
connect="pairs",
pen=pg.mkPen("k", width=1.5),
)
self.xcn = xcn
self.ycn = ycn
p3.addItem(d)
return p3
def voltage_graph(self):
p4 = self.win.addPlot(
title="%s Vm" % self.cell,
row=3,
col=0,
labels={"bottom": "T (ms)", "left": "Vm (mV)"},
)
for nr in range(self.nrep):
p4.plot(
self.time[nr],
self.vms[nr],
pen=pg.mkPen(pg.intColor(nr, self.nrep), hues=self.nrep, width=1.0),
)
return p4
def xmtr_graph(self):
p5 = self.win.addPlot(
title="xmtr", row=0, col=1, labels={"bottom": "T (ms)", "left": "gSyn"}
)
if synapseType == "multisite":
for nr in [0]:
syn = self.synapses[nr]
j = 0
for k in range(self.n_sgc):
synapse = syn[k]
for i in range(synapse.terminal.n_rzones):
p5.plot(
self.time[nr],
self.xmtrs[nr]["xmtr%04d" % j],
pen=pg.mkPen(
pg.intColor(nr, self.nrep),
hues=self.nrep,
width=1.0,
),
)
j = j + 1
return p5
def an_psth_graph(self):
p6 = self.win.addPlot(
title="AN PSTH",
row=1,
col=1,
labels={"bottom": "T (ms)", "left": "Sp/ms/trial"},
)
bins = np.arange(0, 200, 1)
(hist, binedges) = np.histogram(self.xan, bins)
curve6 = p6.plot(
binedges,
hist,
stepMode=True,
fillBrush=(0, 0, 0, 255),
brush=pg.mkBrush("k"),
fillLevel=0,
)
return p6
def cell_psth_graph(self):
p7 = self.win.addPlot(
title="%s PSTH" % self.cell,
row=2,
col=1,
labels={"bottom": "T (ms)", "left": "Sp/ms/trial"},
)
bins = np.arange(0, 200, 1)
(hist, binedges) = np.histogram(self.xcn, bins)
curve7 = p7.plot(
binedges,
hist,
stepMode=True,
fillBrush=(0, 0, 0, 255),
brush=pg.mkBrush("k"),
fillLevel=0,
)
return p7
def run_trial(info):
"""
This function is really the bread
and butter of the run and determines the layout
of the model and the stimulus is
created and delivered by the SGC.
Runs a single trial and returns it
into another dictionary that is stored
before the next trial is run.
:param info: dict containing :'n_sgc': self.n_sgc,
'gmax': self.AMPA_gmax,
'stim': self.stim,
'simulator': self.simulator,
'cf': self.cf, 'sr': self.sr,
'seed': self.seed,
'run_duration': self.run_duration,
'temp': self.temp,
'dt': self.dt,
'init': custom_init
post cell allowed to use defaults in the case of things like pyramidal cells are guinea pigs instead of a mouse
"""
# for the model to change the post_cell needs to be changed here otherwise the model will not be changed.
# special consideration needs to be taken because not all cell parameters are universal
# ex: Pyramidal does not have a species='mouse', nothing just assumes a default and not all defaults are the same
post_cell = cells.Pyramidal.create()
pre_cells = []
synapses = []
xmtr = {}
# connects all of the SGC fibers to the post_cell using simple synapses and then generates a sound stim based on a
# seed the number of repetitions desired
for nsgc, sgc in enumerate(range(info["n_sgc"])):
pre_cells.append(cells.DummySGC(cf=info["cf"], sr=info["sr"]))
synapses.append(pre_cells[-1].connect(post_cell, type="simple"))
synapses[-1].terminal.netcon.weight[0] = info["gmax"]
# sets sounds stim for each of the SGC fibers independently
pre_cells[-1].set_sound_stim(
info["stim"], seed=info["seed"] + nsgc, simulator=info["simulator"]
)
# Recording each trial and returning it as a dictionary
Vm = h.Vector()
Vm.record(post_cell.soma(0.5)._ref_v)
rtime = h.Vector()
rtime.record(h._ref_t)
h.tstop = 1e3 * info["run_duration"] # duration of a run
h.celsius = info["temp"]
h.dt = info["dt"]
post_cell.cell_initialize()
info["init"]()
h.t = 0.0
h.run()
return {
"time": np.array(rtime),
"vm": Vm.to_python(),
"xmtr": xmtr,
"pre_cells": pre_cells,
"post_cell": post_cell,
"synapses": synapses,
}
if __name__ == "__main__":
main()