def simulate_spiking3(parameters): x = Bunch(parameters) tau_m_inv = 1./(x.tau_m*br.ms) tau_e_inv = 1./(x.tau_e*br.ms) tau_i_inv = 1./(x.tau_i*br.ms) tau_a_inv = 1./(x.tau_a*br.ms) GM = generative_model_data(x.Ndic, x.Ndim, x.k, positive_phi=x.positive_phi, positive_input=x.positive_input, seed=x.seed) br.clear(all=True) # clears away all the brian objects from previous simulations. eqs = ''' dvm/dt=((x.v_rest*br.mV-vm) + ge*(x.v_rev_e*br.mV-vm) + gi*(x.v_rev_i*br.mV-vm) + i_s)*tau_m_inv :br.mV dge/dt = -ge*tau_e_inv :1 dgi/dt = -gi*tau_i_inv :1 da/dt = -a*tau_a_inv :br.Hz i_s :br.mV ''' simulation_clock = br.Clock(dt=x.dt*br.ms) recording_clock = br.Clock(dt=1*br.ms) P = br.NeuronGroup(x.Ndic, model=eqs, threshold=x.v_thr*br.mV, reset=x.v_reset*br.mV, refractory=x.t_refr*br.ms, clock=simulation_clock) P.vm = (((np.random.random((x.Ndic))-0.5) * 0.5 * (x.v_rest-x.v_thr)) + x.v_rest) * br.mV P.i_s = x.input_factor * GM["i_stim"] * br.mV P.a = 0 G_exc = GM["G"].copy() G_exc[G_exc>0]=0 G_exc = -1.*G_exc G_inh = GM["G"].copy() G_inh[G_inh<0]=0 Ce = br.Connection(P, P, 'ge') Ce.connect(P, P, x.w_e*G_exc) Ci = br.Connection(P, P, 'gi') Ci.connect(P, P, x.w_i*G_inh) Ca = br.IdentityConnection(P, P, 'a', weight=tau_a_inv) M = br.SpikeMonitor(P) SMs = [] SM_1 = br.StateMonitor(P, "vm", record=True, timestep=1, clock=recording_clock) SM_2 = br.StateMonitor(P, "ge", record=True, timestep=1, clock=recording_clock) SM_3 = br.StateMonitor(P, "gi", record=True, timestep=1, clock=recording_clock) SM_4 = br.StateMonitor(P, "a", record=True, timestep=1, clock=recording_clock) SM_5 = br.StateMonitor(P, "i_s", record=True, timestep=1, clock=recording_clock) SMs.append(SM_1) SMs.append(SM_2) SMs.append(SM_3) SMs.append(SM_4) SMs.append(SM_5) network = br.Network(P, Ce, Ci, Ca, M, *SMs) # starting the simulation network.run(x.t_end*br.ms) return SMs, M, GM
def setup_sims(neuron_params, input_params, duration): fin = input_params.get("fin") fout = input_params.get("fout") weight = input_params.get("weight") num_inp = input_params.get("num_inp") sync_configs = input_params.get("sync") if fin is None: fin = sl.tools.calibrate_frequencies(neuron_params, N_in=num_inp, w_in=weight, f_out=fout, synchrony_conf=sync_configs) brian.clear(True) gc.collect() brian.defaultclock.reinit() neurons = NeuronGroup(N=len(sync_configs), **neuron_params) simulation = Network(neurons) input_groups = [] for idx, (inrate, (sync, jitter)) in enumerate(zip(fin, sync_configs)): inp_grp = sl.tools.fast_synchronous_input_gen(num_inp, inrate*Hz, sync, jitter, duration) simulation.add(inp_grp) inp_conn = Connection(inp_grp, neurons[idx], state='V', weight=weight) input_groups.append(inp_grp) simulation.add(inp_conn) tracemon = StateMonitor(neurons, 'V', record=True) spikemon = SpikeMonitor(neurons) inputmons = [SpikeMonitor(igrp) for igrp in input_groups] simulation.add(tracemon, spikemon, inputmons) monitors = {"inputs": inputmons, "outputs": spikemon, "traces": tracemon} return simulation, monitors
def run_network(self, traj): """Top-level simulation function, pass this to the environment Performs an individual network run during parameter exploration. `run_network` does not need to be called by the user. If the top-level `~pypet.brian.network.run_network` method (not this one of the NetworkManager) is passed to an :class:`~pypet.environment.Environment` with this NetworkManager, `run_network` and :func:`~pypet.brian.network.NetworkManager.build` are automatically called for each individual experimental run. This function will create a new `BRIAN network`_ in case one was not pre-run. The execution of the network run is carried out by the :class:`~pypet.brian.network.NetworkRunner` and it's :func:`~pypet.brian.network.NetworkRunner.execute_network_run` (also take a look at this function's documentation to see the structure of a network run). .. `BRIAN network`_: http://briansimulator.org/docs/reference-network.html#brian.Network :param traj: Trajectory container """ # Check if the network was pre-built if self._pre_built: # If yes check for multiprocessing or if a single core processing is forced multiproc = traj.f_get("config.environment.%s.multiproc" % traj.v_environment_name).f_get() if multiproc: self._run_network(traj) else: if self._force_single_core: self._logger.warning( "Running Single Core Mode. Be aware that the network " "evolves over ALL your runs and is not reset. " "Use this setting only for debugging purposes " "because your results will be not correct in case " "your trajectory contains more than a single run. " ) self._run_network(traj) else: raise RuntimeError( "You cannot run a pre-built network without " "multiprocessing.\n" "The network configuration must be copied either by " "pickling (using a `multiproc=True` and `use_pool=True` in " "your environment) or by forking ( multiprocessing with " "`use_pool=False`).\n If your network " "cannot be pickled use the latter. " "In order to come close to iterative processing " "you could use multiprocessing with `ncores=1`. \n" "If you do not care about messing up initial conditions " "(i.e. you are debugging) use `force_single_core=True` " "in your network manager." ) else: clear(True, True) reinit() self._run_network(traj)
def run_network(self, traj): """Top-level simulation function, pass this to the environment Performs an individual network run during parameter exploration. `run_network` does not need to be called by the user. If the top-level `~pypet.brian.network.run_network` method (not this one of the NetworkManager) is passed to an :class:`~pypet.environment.Environment` with this NetworkManager, `run_network` and :func:`~pypet.brian.network.NetworkManager.build` are automatically called for each individual experimental run. This function will create a new `BRIAN network`_ in case one was not pre-run. The execution of the network run is carried out by the :class:`~pypet.brian.network.NetworkRunner` and it's :func:`~pypet.brian.network.NetworkRunner.execute_network_run` (also take a look at this function's documentation to see the structure of a network run). .. `BRIAN network`_: http://briansimulator.org/docs/reference-network.html#brian.Network :param traj: Trajectory container """ # Check if the network was pre-built if self._pre_built: # If yes check for multiprocessing or if a single core processing is forced multiproc = traj.f_get('config.environment.%s.multiproc' % traj.v_environment_name).f_get() if multiproc: self._run_network(traj) else: if self._force_single_core: self._logger.warning( 'Running Single Core Mode. Be aware that the network ' 'evolves over ALL your runs and is not reset. ' 'Use this setting only for debugging purposes ' 'because your results will be not correct in case ' 'your trajectory contains more than a single run. ') self._run_network(traj) else: raise RuntimeError( 'You cannot run a pre-built network without ' 'multiprocessing.\n' 'The network configuration must be copied either by ' 'pickling (using a `multiproc=True` and `use_pool=True` in ' 'your environment) or by forking ( multiprocessing with ' '`use_pool=False`).\n If your network ' 'cannot be pickled use the latter. ' 'In order to come close to iterative processing ' 'you could use multiprocessing with `ncores=1`. \n' 'If you do not care about messing up initial conditions ' '(i.e. you are debugging) use `force_single_core=True` ' 'in your network manager.') else: clear(True, True) reinit() self._run_network(traj)
def simulate_rate4(parameters): x = Bunch(parameters) GM = generative_model_data(x.Ndic, x.Ndim, x.k, positive=x.positive_GM, seed=x.seed) tau_m_inv = 1./(x.tau_m*br.ms) br.clear(all=True) # clears away all the brian objects from previous simulations. def thresh_func(values, threshold, thr_type, thr_coeff, nonnegative): vals = values.copy() if not nonnegative: vals[(vals<threshold) & (vals>-threshold)]=0. if thr_type == "soft": vals[(vals>threshold)] -= threshold vals[(vals<-threshold)] += threshold else: vals[(vals<threshold)]=0. if thr_type == "soft": vals[(vals>threshold)] -= threshold return thr_coeff * vals eqs = ''' du/dt=(-u-li+i_s)*tau_m_inv :br.Hz a :br.Hz i_s :br.Hz li :br.Hz ''' simulation_clock = br.Clock(dt=x.dt*br.ms) recording_clock = br.Clock(dt=1*br.ms) P = br.NeuronGroup(x.Ndic, model=eqs, threshold=200000*br.Hz, clock=simulation_clock) P.i_s = x.input_factor * GM["i_stim"] P.a = 0 @br.network_operation(clock=simulation_clock, when="end") def set_input(simulation_clock): P.li = np.dot(GM["G"], P.a) P.a = thresh_func(P.u, x.threshold, x.thr_type, x.thr_coeff, x.nonnegative) SMs = [] SM_2 = br.StateMonitor(P, "a", record=True, timestep=1, clock=recording_clock) SMs.append(SM_2) network = br.Network(P, set_input, *SMs) # starting the simulation network.run(x.t_end*br.ms) return 1.*SM_2[:][:,-1]/x.input_factor, GM
def run_sim(number_neurons=default_number_neurons, connection_probability=default_connection_probability, synaptic_weights=default_synaptic_weights, synaptic_time_constant=default_synaptic_time_constant, tend=300): '''run a simulation of a population of leaky integrate-and-fire excitatory neurons that are randomly connected. The population is injected with a transient current.''' from brian.units import mvolt, msecond, namp, Mohm import brian brian.clear() El = 0 * mvolt tau_m = 30 * msecond tau_syn = synaptic_time_constant * msecond R = 20 * Mohm v_threshold = 30 * mvolt v_reset = 0 * mvolt tau_refractory = 4 * msecond eqs = brian.Equations(''' dv/dt = (-(v - El) + R*I)/tau_m : volt I = I_syn + I_stim : amp dI_syn/dt = -I_syn/tau_syn : amp I_stim : amp ''') external_current = np.zeros(tend) external_current[np.arange(0, 100)] = 5 * namp group = brian.NeuronGroup( model=eqs, N=number_neurons, threshold=v_threshold, reset=v_reset, refractory=tau_refractory) group.I_stim = brian.TimedArray(external_current, dt=1*msecond) connections = brian.Connection(group, group, 'I_syn') connections.connect_random(sparseness=connection_probability, weight=synaptic_weights*namp) spike_monitor = brian.SpikeMonitor(group) population_rate_monitor = brian.PopulationRateMonitor(group, bin=10*msecond) brian.reinit() brian.run(tend * msecond) return spike_monitor, population_rate_monitor
def poisson_input(active, N_input, r, time_input, t1, t2): "function to built a poisson input" "with no zero firing rates" from brian import PoissonGroup,SpikeMonitor,reinit,clear,run,Hz,second import random as pyrandom reinit(states = True) clear(erase = True, all = True) N = 1000 P = PoissonGroup(N) S = SpikeMonitor(P) run(t1) P.rate = r run(time_input) P.rate = 0*Hz run(t2) s = [] remove = [] for i in xrange(N): s.append(len(S[i])) if len(S[i]) == 0: remove.append(i) pos = [x for x in range(N) if x not in remove] pos = pyrandom.sample(pos, len(active)) C = [] for ii in xrange(len(pos)): D = list(S.spiketimes[pos[ii]]) D = [(active[ii],x) for x in D] C += D C = [(i,t *second) for (i,t) in C] C = sorted(C, key=lambda x: x[1]) reinit(states = True) clear(erase = True, all = True) return C
def simulate_rate5(parameters): x = Bunch(parameters) tau_m_inv = 1./(x.tau_m*br.ms) br.clear(all=True) # clears away all the brian objects from previous simulations. assert x.thresh_func, "you have to provide a threshold function" eqs = ''' du/dt=(-u-li+i_s)*tau_m_inv :br.Hz a :br.Hz i_s :br.Hz li :br.Hz ''' simulation_clock = br.Clock(dt=x.dt*br.ms) recording_clock = br.Clock(dt=1*br.ms) P = br.NeuronGroup(x.Ndic, model=eqs, threshold=200000*br.Hz, clock=simulation_clock) P.i_s = x.input_factor * x.GM["i_stim"] P.a = 0 @br.network_operation(clock=simulation_clock, when="end") def set_input(simulation_clock): P.li = np.dot(x.GM["G"], P.a) P.a = x.thresh_func(P.u, x.threshold) SMs = [] SM_2 = br.StateMonitor(P, "a", record=True, timestep=1, clock=recording_clock) SMs.append(SM_2) network = br.Network(P, set_input, *SMs) # starting the simulation network.run(x.t_end*br.ms) return 1.*SM_2[:]
def run_simulation(realizations=1, trials=1, t=3000 * ms, alpha=1, ree=1, k=50, winlen=50 * ms, verbose=True, t_stim=0): """ Run the whole simulation with the specified parameters. All model parameter are set in the function. Keyword arguments: :param realizations: number of repititions of the whole simulation, number of network instances :param trials: number of trials for network instance :param t: simulation time :param alpha: scaling factor for number of neurons in the network :param ree: clustering coefficient :param k: number of clusters :param t_stim : duration of stimulation of a subset of clusters :param winlen: length of window in ms :param verbose: plotting flag :return: numpy matrices with spike times """ # The equations defining our neuron model eqs_string = """ dV/dt = (mu - V)/tau + x: volt dx/dt = -1.0/tau_2*(x - y/tau_1) : volt/second dy/dt = -y/tau_1 : volt mu : volt tau: second tau_2: second tau_1: second """ # Model parameters n_e = int(4000 * alpha) # number of exc neurons n_i = int(1000 * alpha) # number of inh neurons tau_e = 15 * ms # membrane time constant (for excitatory synapses) tau_i = 10 * ms # membrane time constant (for inhibitory synapses) tau_syn_2_e = 3 * ms # exc synaptic time constant tau2 in paper tau_syn_2_i = 2 * ms # inh synaptic time constant tau2 in paper tau_syn_1 = 1 * ms # exc/inh synaptic time constant tau1 in paper vt = -50 * mV # firing threshold vr = -65 * mV # reset potential dv = vt - vr # delta v refrac = 5 * ms # absolute refractory period # scale the weights to ensure same variance in the inputs wee = 0.024 * dv * np.sqrt(1.0 / alpha) wie = 0.014 * dv * np.sqrt(1.0 / alpha) wii = -0.057 * dv * np.sqrt(1.0 / alpha) wei = -0.045 * dv * np.sqrt(1.0 / alpha) # Connection probability p_ee = 0.2 p_ii = 0.5 p_ie = 0.5 p_ei = 0.5 # determine probs for inside and outside of clusters p_in, p_out = get_cluster_connection_probs(ree, k, p_ee) mu_min_e, mu_max_e = 1.1, 1.2 mu_min_i, mu_max_i = 1.0, 1.05 # increase cluster weights if there are clusters wee_cluster = wee if p_in == p_out else 1.9 * wee # define numpy array for data storing all_data = np.zeros((realizations, trials, n_e + n_i, int(t / winlen) // 2)) for realization in range(realizations): # clear workspace to make sure that is a new realization of the network clear(True, True) reinit() # set up new random bias parameter for every type of neuron mu_e = vr + np.random.uniform(mu_min_e, mu_max_e, n_e) * dv # bias for excitatory neurons mu_i = vr + np.random.uniform(mu_min_i, mu_max_i, n_i) * dv # bias for excitatory neurons # Let's create an equation object from our string and parameters model_eqs = Equations(eqs_string) # Let's create 5000 neurons all_neurons = NeuronGroup( N=n_e + n_i, model=model_eqs, threshold=vt, reset=vr, refractory=refrac, freeze=True, method="Euler", compile=True, ) # Divide the neurons into excitatory and inhibitory ones neurons_e = all_neurons[0:n_e] neurons_i = all_neurons[n_e : n_e + n_i] # set the bias neurons_e.mu = mu_e neurons_i.mu = mu_i neurons_e.tau = tau_e neurons_i.tau = tau_i neurons_e.tau_2 = tau_syn_2_e neurons_i.tau_2 = tau_syn_2_i all_neurons.tau_1 = tau_syn_1 # set up connections connections = Connection(all_neurons, all_neurons, "y") # do the cluster connection like cross validation: cluster neuron := test idx; other neurons := train idx kf = KFold(n=n_e, n_folds=k) for idx_out, idx_in in kf: # idx_out holds all other neurons; idx_in holds all cluster neurons # connect current cluster to itself connections.connect_random( all_neurons[idx_in[0] : idx_in[-1]], all_neurons[idx_in[0] : idx_in[-1]], sparseness=p_in, weight=wee_cluster, ) # connect current cluster to other neurons connections.connect_random( all_neurons[idx_in[0] : idx_in[-1]], all_neurons[idx_out[0] : idx_out[-1]], sparseness=p_out, weight=wee ) # connect all excitatory to all inhibitory, irrespective of clustering connections.connect_random(all_neurons[0:n_e], all_neurons[n_e : (n_e + n_i)], sparseness=p_ie, weight=wie) # connect all inhibitory to all excitatory connections.connect_random(all_neurons[n_e : (n_e + n_i)], all_neurons[0:n_e], sparseness=p_ei, weight=wei) # connect all inhibitory to all inhibitory connections.connect_random( all_neurons[n_e : (n_e + n_i)], all_neurons[n_e : (n_e + n_i)], sparseness=p_ii, weight=wii ) # set up spike monitors spike_mon_e = SpikeMonitor(neurons_e) spike_mon_i = SpikeMonitor(neurons_i) # set up network with monitors network = Network(all_neurons, connections, spike_mon_e, spike_mon_i) # run this network for some number of trials, every time with for trial in range(trials): # different initial values all_neurons.V = vr + (vt - vr) * np.random.rand(len(all_neurons)) * 1.4 # Calibration phase # run for the first half of the time to let the neurons adapt network.run(t / 2) # reset monitors to start recording phase spike_mon_i.reinit() spike_mon_e.reinit() # stimulation if duration is given # define index variable for the stimulation possibility (is 0 for stimulation time=0) t_stim_idx = int(t_stim / (winlen / ms)) if not (t_stim == 0): # Stimulation phase, increase input to subset of clusters all_neurons[:400].mu += 0.07 * dv network.run(t_stim * ms, report="text") # set back to normal all_neurons[:400].mu -= 0.07 * dv # save data all_data[realization, trial, :n_e, :t_stim_idx] = spikes_counter(spike_mon_e, winlen) all_data[realization, trial, n_e:, :t_stim_idx] = spikes_counter(spike_mon_i, winlen) # reset monitors spike_mon_e.reinit() spike_mon_i.reinit() # run the remaining time of the simulation network.run((t / 2) - t_stim * ms, report="text") # save results all_data[realization, trial, :n_e, t_stim_idx:] = spikes_counter(spike_mon_e, winlen) all_data[realization, trial, n_e:, t_stim_idx:] = spikes_counter(spike_mon_i, winlen) if verbose: plt.ion() plt.figure() raster_plot(spike_mon_e) plt.title("Excitatory neurons") spike_mon_e.reinit() spike_mon_i.reinit() return all_data
def runsim(Nin, weight, fout, sync): sim = Network() clear(True) gc.collect() defaultclock.reinit() duration = 5*second lifeq = "dV/dt = -V/(10*ms) : volt" nrndef = {"model": lifeq, "threshold": "V>=15*mV", "reset": "V=0*mV", "refractory": 2*ms} fin = load_or_calibrate(nrndef, Nin, weight, sync, fout, Vth=15*mV, tau=10*ms) # print("Calibrated frequencies:") # print(", ".join(str(f) for f in fin)) inputgroups = [] connections = [] neurons = [] Nneurons = len(fin) neurons = NeuronGroup(Nneurons, **nrndef) for idx in range(Nneurons): fin_i = fin[idx] sync_i, sigma_i = sync[idx] inputgrp = sl.tools.fast_synchronous_input_gen(Nin, fin_i, sync_i, sigma_i, duration) defaultclock.reinit() conn = Connection(inputgrp, neurons[idx], state="V", weight=weight) inputgroups.append(inputgrp) connections.append(conn) voltagemon = StateMonitor(neurons, "V", record=True) spikemon = SpikeMonitor(neurons, record=True) sim.add(neurons, voltagemon, spikemon) sim.add(*inputgroups) sim.add(*connections) print("Running {} {} {}".format(Nin, weight, fout)) sim.run(duration, report="stdout") mnpss = [] allnpss = [] for idx in range(Nneurons): vmon = voltagemon[idx] smon = spikemon[idx] # print("Desired firing rate: {}".format(fout)) # print("Actual firing rate: {}".format(len(smon)/duration)) if len(smon) > 0: npss = sl.tools.npss(vmon, smon, 0*mV, 15*mV, 10*ms, 2*ms) else: npss = 0 mnpss.append(np.mean(npss)) allnpss.append(npss) nrndeftuple = tuple(nrndef.items()) key = (nrndeftuple, Nin, weight, tuple(sync), fout, 15*mV, 10*ms) save_data(key, allnpss) imshape = (len(sigma), len(Sin)) imextent = (0, 1, 0, 4.0) mnpss = np.reshape(mnpss, imshape, order="F") plt.figure() plt.imshow(mnpss, aspect="auto", origin="lower", extent=imextent, interpolation="none", vmin=0, vmax=1) cbar = plt.colorbar() cbar.set_label("$\overline{M}$") plt.xlabel("$S_{in}$") plt.ylabel("$\sigma_{in}$ (ms)") filename = "npss_{}_{}_{}".format(Nin, weight, fout).replace(".", "") plt.savefig(filename+".pdf") plt.savefig(filename+".png") print("{} saved".format(filename)) voltages = voltagemon.values spiketrains = spikemon.spiketimes.values() pickle.dump({"voltages": voltages, "spiketrains": spiketrains}, open(filename+".pkl", 'w')) return voltagemon, spikemon
def run_sim(ffExcInputMult=None, ffInhInputMult=None): """Run the cond-based LIF neuron simulation. Takes a few minutes to construct network and run Parameters ---------- ffExcInputMult: scalar: FF input magnitude to E cells. multiply ffInputV by this value and connect to E cells ffInhInputMult: scalar: FF input magnitude to I cells. Returns ------- outDict - spike times, records of continuous values from simulation """ # use helper to get input timecourses (ffInputV, condAddV) = create_input_vectors( doDebugPlot=False) # multiplied by scalars below # setup initial state stT = time.time() brian.set_global_preferences(usecodegen=True) brian.set_global_preferences(useweave=True) brian.set_global_preferences(usecodegenweave=True) brian.clear(erase=True, all=True) brian.reinit_default_clock() clk = brian.Clock(dt=0.05 * ms) ################ # create neurons, define connections neurNetwork = brian.NeuronGroup(nNet, model=eqs, threshold=vthresh, reset=vrest, refractory=absRefractoryMs * msecond, order=1, compile=True, freeze=False, clock=clk) # create neuron pools neurCE = neurNetwork.subgroup(nExc) neurCI = neurNetwork.subgroup(nInh) connCE = brian.Connection(neurCE, neurNetwork, 'ge') connCI = brian.Connection(neurCI, neurNetwork, 'gi') print('n cells: %d, nE,I %d,%d, %s, absRefractoryMs: %d' % (nNet, nExc, nInh, repr(clk), absRefractoryMs)) # connect the network to itself connCE.connect_random(neurCE, neurNetwork, internalSparseness, weight=connENetWeight) connCI.connect_random(neurCI, neurNetwork, internalSparseness, weight=connINetWeight) # connect inputs that change spont rate assert ( spontAddRate <= 0 ), 'Spont add rate should be negative - convention: neg, excite inhibitory cells' spontAddNInpSyn = 100 nTotalSpontNeurons = (spontAddNInpSyn * nInh * 0.02) neurSpont = brian.PoissonGroup(nTotalSpontNeurons, -1.0 * spontAddRate * Hz) connCSpont = brian.Connection(neurSpont, neurCI, 'ge') connCSpont.connect_random( p=spontAddNInpSyn * 1.0 / nTotalSpontNeurons, weight=connENetWeight, # match internal excitatory strengths fixed=True) # connect the feedforward visual (poisson) inputs to excitatory cells (ff E) ffExcInputNInpSyn = 100 nTotalFfNeurons = (ffExcInputNInpSyn * ffExcInputNTargs * 0.02 ) # one pop of input cells for both E and I FF _ffExcInputV = ffExcInputMult * np.abs(a_(ffInputV).copy()) assert (np.all( _ffExcInputV >= 0)), 'Negative FF rates are rectified to zero' neurFfExcInput = brian.PoissonGroup( nTotalFfNeurons, lambda t: _ffExcInputV[int(t * 1000)] * Hz) connCFfExcInput = brian.Connection(neurFfExcInput, neurNetwork, 'ge') connCFfExcInput.connect_random(neurFfExcInput, neurCE[0:ffExcInputNTargs], ffExcInputNInpSyn * 1.0 / nTotalFfNeurons, weight=connENetWeight, fixed=True) # connect the feedforward visual (poisson) inputs to inhibitory cells (ff I) ffInhInputNInpSyn = 100 _ffInhInputV = ffInhInputMult * np.abs(ffInputV.copy()) assert (np.all( _ffInhInputV >= 0)), 'Negative FF rates are rectified to zero' neurFfInhInput = brian.PoissonGroup( nTotalFfNeurons, lambda t: _ffInhInputV[int(t * 1000)] * Hz) connCFfInhInput = brian.Connection(neurFfInhInput, neurNetwork, 'ge') connCFfInhInput.connect_random( neurFfInhInput, neurCI[0:ffInhInputNTargs], ffInhInputNInpSyn * 1.0 / nTotalFfNeurons, # sparseness weight=connENetWeight, fixed=True) # connect added step (ChR2) conductance to excitatory cells condAddAmp = 4.0 gAdd = brian.TimedArray(condAddAmp * condAddV, dt=1 * ms) print('Adding conductance for %d cells (can be slow): ' % len(condAddNeurNs), end=' ') for (iN, tN) in enumerate(condAddNeurNs): neurCE[tN].gAdd = gAdd print('done') # Initialize using some randomness so all neurons don't start in same state. # Alternative: initialize with constant values, give net extra 100-300ms to evolve from initial state. neurNetwork.v = (brian.randn(1) * 5.0 - 65) * mvolt neurNetwork.ge = brian.randn(nNet) * 1.5 + 4 neurNetwork.gi = brian.randn(nNet) * 12 + 20 # Record continuous variables and spikes monSTarg = brian.SpikeMonitor(neurNetwork) if contRecNs is not None: contRecClock = brian.Clock(dt=contRecStepMs * ms) monVTarg = brian.StateMonitor(neurNetwork, 'v', record=contRecNs, clock=contRecClock) monGETarg = brian.StateMonitor(neurNetwork, 'ge', record=contRecNs, clock=contRecClock) monGAddTarg = brian.StateMonitor(neurNetwork, 'gAdd', record=contRecNs, clock=contRecClock) monGITarg = brian.StateMonitor(neurNetwork, 'gi', record=contRecNs, clock=contRecClock) # construct brian.Network before running (so brian explicitly knows what to update during run) netL = [ neurNetwork, connCE, connCI, monSTarg, neurFfExcInput, connCFfExcInput, neurFfInhInput, connCFfInhInput, neurSpont, connCSpont ] if contRecNs is not None: # noinspection PyUnboundLocalVariable netL.append([monVTarg, monGETarg, monGAddTarg, monGITarg]) # cont monitors net = brian.Network(netL) print("Network construction time: %3.1f seconds" % (time.time() - stT)) # run print("Simulation running...") sys.stdout.flush() start_time = time.time() net.run(simRunTimeS * second, report='text', report_period=30.0 * second) durationS = time.time() - start_time print("Simulation time: %3.1f seconds" % durationS) outNTC = collections.namedtuple( 'outNTC', 'vm ge gadd gi clockDtS clockStartS clockEndS spiketimes contRecNs') outNTC.__new__.__defaults__ = (None, ) * len( outNTC._fields) # default to None outNT = outNTC(clockDtS=float(monSTarg.clock.dt), clockStartS=float(monSTarg.clock.start), clockEndS=float(monSTarg.clock.end), spiketimes=a_(monSTarg.spiketimes.values(), dtype='O'), contRecNs=contRecNs) if contRecNs is not None: outNT = outNT._replace(vm=monVTarg.values, ge=monGETarg.values, gadd=monGAddTarg.values, gi=monGITarg.values) return outNT
import brian import numpy as np import os, sys nruns = int(sys.argv[1]) for nrun in xrange(1, nruns + 1): brian.seed(nrun) print 'RUN: ' + str(nrun) brian.reinit(states=True) brian.clear(erase=True, all=True) rate = int(sys.argv[2]) foldername = 'rate' + str(rate) + '/run_' + str(nrun) os.system('mkdir -p -v ' + foldername) N = 1000 time_input = 23000 * brian.ms P = brian.PoissonGroup(N) S = brian.SpikeMonitor(P) P.rate = rate * brian.Hz brian.run(time_input, report='text', report_period=10 * brian.second) fname = 'noise_' for s in xrange(len(S.spiketimes)): spiketimes = [round(1000 * x, 1) + 50 for x in list(S.spiketimes[s])] np.savetxt(foldername + '/' + fname + str(s) + '.txt', spiketimes, fmt='%10.1f', newline='\n')
def runsim(fin): clear(True) gc.collect() defaultclock.reinit() weight = 0.16*mV sim = Network() duration = 2.0*second Vth = 15*mV Vreset = 13.65*mV trefr = 2*ms lifeq = """ dV/dt = -V/(10*ms) : volt Vth : volt """ nrndef = {"model": lifeq, "threshold": "V>=Vth", "reset": "V=Vreset", "refractory": 0.1*ms} inputgroups = [] connections = [] neurons = [] Nneurons = len(fin) neurons = NeuronGroup(Nneurons, **nrndef) neurons.V = 0*mV neurons.Vth = 15*mV for idx in range(Nneurons): fin_i = fin[idx]*Hz inputgrp = PoissonGroup(50, fin_i) conn = Connection(inputgrp, neurons[idx], state="V", weight=weight) inputgroups.append(inputgrp) connections.append(conn) voltagemon = StateMonitor(neurons, "V", record=True) spikemon = SpikeMonitor(neurons, record=True) sim.add(neurons, voltagemon, spikemon) sim.add(*inputgroups) sim.add(*connections) @network_operation def refractory_threshold(clock): for idx in range(Nneurons): if (len(spikemon.spiketimes[idx]) and clock.t < spikemon.spiketimes[idx][-1]*second+trefr): neurons.Vth[idx] = 100*mV else: neurons.Vth[idx] = Vth sim.add(refractory_threshold) print("Running simulation of {} neurons for {} s".format(Nneurons, duration)) sim.run(duration, report="stdout") mnpss = [] allnpss = [] outisi = [] for idx in range(Nneurons): vmon = voltagemon[idx] smon = spikemon[idx] if not len(smon): continue outisi.append(duration*1000/len(smon)) if len(smon) > 0: npss = sl.tools.npss(vmon, smon, 0*mV, 15*mV, 10*ms, 2*ms) else: npss = 0 mnpss.append(np.mean(npss)) allnpss.append(npss) return outisi, mnpss
def tearDownClass(cls): clear(True, True) reload(brian)
def fft_std(delta_u, run_num, new_connectivity, osc, rep): #bn.seed(int(time.time())) bn.reinit_default_clock() #bn.seed(1412958308+2) bn.defaultclock.dt = 0.5 * bn.ms #============================================================================== # Define constants for the model. #============================================================================== fft_file = './std_fft_p20_' rate_file = './std_rate_p20_' print delta_u print run_num print new_connectivity print rep if osc: T = 5.5 * bn.second else: T = 2.5 * bn.second n_tsteps = T / bn.defaultclock.dt fft_start = 0.5 * bn.second / bn.defaultclock.dt # Time window for the FFT computation ro = 1.2 * bn.Hz SEE1 = 1.0 SEE2 = 1.0 qee1 = 1.00 # Fraction of NMDA receptors for e to e connections qee2 = 0.00 qie1 = 1.00 # Fraction of NMDA receptors for e to i connections qie2 = 0.00 uee1 = 0.2 - delta_u uee2 = 0.2 + delta_u uie1 = 0.2 uie2 = 0.2 trec1 = 1000.0 * bn.ms trec2 = 1000.0 * bn.ms k = 0.65 #Jeo_const = 1.0#*bn.mV # Base strength of o (external) to e connections Ne = 3200 # number of excitatory neurons Ni = 800 # number of inhibitory neurons No = 20000 # number of external neurons N = Ne + Ni pcon = 0.2 # probability of connection Jee = 10.0 / (Ne * pcon) Jie = 10.0 / (Ne * pcon) Jii = k * 10.0 / (Ni * pcon) Jei = k * 10.0 / (Ni * pcon) Jeo = 1.0 El = -60.0 * bn.mV # leak reversal potential Vreset = -52.0 * bn.mV # reversal potential Vthresh = -40.0 * bn.mV # spiking threshold tref = 2.0 * bn.ms # refractory period te = 20.0 * bn.ms # membrane time constant of excitatory neurons ti = 10.0 * bn.ms # membrane time constant of inhibitory neruons tee_ampa = 10.0 * bn.ms # time const of ampa currents at excitatory neurons tee_nmda = 100.0 * bn.ms # time const of nmda currents at excitatory neurons tie_ampa = 10.0 * bn.ms # time const of ampa currents at inhibitory neurons tie_nmda = 100.0 * bn.ms # time const of nmda currents at inhibitory neurons tii_gaba = 10.0 * bn.ms # time const of GABA currents at inhibitory neurons tei_gaba = 10.0 * bn.ms # time const of GABA currents at excitatory neurons teo_input = 100.0 * bn.ms #============================================================================== # Define model structure #============================================================================== model = ''' dV/dt = (-(V-El)+J_ampa1*I_ampa1+J_nmda1*I_nmda1+J_ampa2*I_ampa2+J_nmda2*I_nmda2-J_gaba*I_gaba+J_input*I_input+eta)/tm : bn.volt dI_ampa1/dt = -I_ampa1/t_ampa : bn.volt dI_nmda1/dt = -I_nmda1/t_nmda : bn.volt dI_ampa2/dt = -I_ampa2/t_ampa : bn.volt dI_nmda2/dt = -I_nmda2/t_nmda : bn.volt dI_gaba/dt = -I_gaba/t_gaba : bn.volt dI_input/dt = (-I_input+mu)/t_input : bn.volt dx1/dt = (1-x1)/t1_rec : 1 dx2/dt = (1-x2)/t2_rec : 1 u1 : 1 t1_rec : bn.second u2 : 1 t2_rec : bn.second mu : bn.volt eta : bn.volt J_ampa1 : 1 J_nmda1 : 1 J_ampa2 : 1 J_nmda2 : 1 J_gaba : 1 J_input : 1 tm : bn.second t_ampa : bn.second t_nmda : bn.second t_gaba : bn.second t_input : bn.second ''' P_reset = "V=-52*bn.mV;x1+=-u1*x1;x2+=-u2*x2" Se_model = ''' we_ampa1 : bn.volt we_nmda1 : bn.volt we_ampa2 : bn.volt we_nmda2 : bn.volt ''' Se_pre = ('I_ampa1 += x1_pre*we_ampa1', 'I_nmda1 += x1_pre*we_nmda1', 'I_ampa2 += x2_pre*we_ampa2', 'I_nmda2 += x2_pre*we_nmda2') Si_model = ''' wi_gaba : bn.volt ''' Si_pre = 'I_gaba += wi_gaba' So_model = ''' wo_input : bn.volt ''' So_pre = 'I_input += wo_input' #============================================================================== # Define populations #============================================================================== P = bn.NeuronGroup(N, model, threshold=Vthresh, reset=P_reset, refractory=tref) Pe = P[0:Ne] Pe.tm = te Pe.t_ampa = tee_ampa Pe.t_nmda = tee_nmda Pe.t_gaba = tei_gaba Pe.t_input = teo_input Pe.I_ampa1 = 0 * bn.mV Pe.I_nmda1 = 0 * bn.mV Pe.I_ampa2 = 0 * bn.mV Pe.I_nmda2 = 0 * bn.mV Pe.I_gaba = 0 * bn.mV Pe.I_input = 0 * bn.mV Pe.V = (np.random.rand(Pe.V.size) * 12 - 52) * bn.mV Pe.x1 = 1.0 Pe.x2 = 1.0 Pe.u1 = uee1 Pe.u2 = uee2 Pe.t1_rec = trec1 Pe.t2_rec = trec2 Pi = P[Ne:(Ne + Ni)] Pi.tm = ti Pi.t_ampa = tie_ampa Pi.t_nmda = tie_nmda Pi.t_gaba = tii_gaba Pi.t_input = teo_input Pi.I_ampa1 = 0 * bn.mV Pi.I_nmda1 = 0 * bn.mV Pi.I_ampa2 = 0 * bn.mV Pi.I_nmda2 = 0 * bn.mV Pi.I_gaba = 0 * bn.mV Pi.I_input = 0 * bn.mV Pi.V = (np.random.rand(Pi.V.size) * 12 - 52) * bn.mV Pi.x1 = 1.0 Pi.x2 = 1.0 Pi.u1 = 0.0 Pi.u2 = 0.0 Pi.t1_rec = 1.0 Pi.t2_rec = 1.0 Pe.J_ampa1 = Jee * (1 - qee1) #*SEE1 Pe.J_nmda1 = Jee * qee1 #*SEE1 Pe.J_ampa2 = Jee * (1 - qee2) #*SEE2 Pe.J_nmda2 = Jee * qee2 #*SEE2 Pi.J_ampa1 = Jie * (1 - qie2) #*SEE2 Pi.J_nmda1 = Jie * qie2 #*SEE2 Pi.J_ampa2 = Jie * (1 - qie1) #*SEE1 Pi.J_nmda2 = Jie * qie1 #*SEE1 Pe.J_gaba = Jei Pi.J_gaba = Jii Pe.J_input = Jeo Pi.J_input = Jeo #============================================================================== # Define inputs #============================================================================== if osc: Pe.mu = 12.0 * bn.mV holder = np.zeros((n_tsteps, )) t_freq = np.linspace(0, 10, n_tsteps) fo = 0.2 # Smallest frequency in the signal fe = 10.0 # Largest frequency in the signal F = int(fe / 0.2) for m in range(1, F + 1): holder = holder + np.cos(2 * np.pi * m * fo * t_freq - m * (m - 1) * np.pi / F) holder = holder / np.max(holder) Pe.eta = bn.TimedArray(0.0 * bn.mV * holder) #, dt=0.5*bn.ms) Background_eo = bn.PoissonInput(Pe, N=1000, rate=1.05 * bn.Hz, weight=0.2 * bn.mV, state='I_input') Background_io = bn.PoissonInput(Pi, N=1000, rate=1.0 * bn.Hz, weight=0.2 * bn.mV, state='I_input') Pi.mu = 0 * bn.mV Pi.eta = 0 * bn.mV #, dt=0.5*bn.ms) Po = bn.PoissonGroup(No, rates=0 * bn.Hz) else: Background_eo = bn.PoissonInput(Pe, N=1000, rate=1.05 * bn.Hz, weight=0.2 * bn.mV, state='I_input') Background_io = bn.PoissonInput(Pi, N=1000, rate=1.0 * bn.Hz, weight=0.2 * bn.mV, state='I_input') holder_pe = np.zeros((n_tsteps, )) time_steps = np.linspace(0, T / bn.second, n_tsteps) holder_pe[time_steps < 0.5] = 0.0 * bn.mV holder_pe[time_steps >= 0.5] = 6.0 * bn.mV #25 holder_pe[time_steps > 1.5] = 0.0 * bn.mV #25 Pe.mu = bn.TimedArray(holder_pe) def firing_function(t, ro): if t > 0.5 * bn.second and t < 3.5 * bn.second: return 0.0 * bn.Hz else: return 0.0 * bn.Hz Pe.eta = 0 * bn.mV #, dt=0.5*bn.ms) Pi.mu = 0.0 * bn.mV Pi.eta = 0 * bn.mV #, dt=0.5*bn.ms) Po = bn.PoissonGroup(No, rates=lambda t: firing_function(t, ro)) #============================================================================== # Define synapses #============================================================================== See1 = bn.Synapses(Pe, Pe, model=Se_model, pre=Se_pre) See2 = bn.Synapses(Pe, Pe, model=Se_model, pre=Se_pre) Sie1 = bn.Synapses(Pe, Pi, model=Se_model, pre=Se_pre) Sie2 = bn.Synapses(Pe, Pi, model=Se_model, pre=Se_pre) Sei = bn.Synapses(Pi, Pe, model=Si_model, pre=Si_pre) Sii = bn.Synapses(Pi, Pi, model=Si_model, pre=Si_pre) Seo = bn.Synapses(Po, Pe, model=So_model, pre=So_pre) #============================================================================== # Define random connections #============================================================================== if new_connectivity: See1.connect_random(Pe, Pe, sparseness=pcon / 2.0) See2.connect_random(Pe, Pe, sparseness=pcon / 2.0) Sie1.connect_random(Pe, Pi, sparseness=pcon / 2.0) Sie2.connect_random(Pe, Pi, sparseness=pcon / 2.0) Sii.connect_random(Pi, Pi, sparseness=pcon) Sei.connect_random(Pi, Pe, sparseness=pcon) Seo.connect_random(Po, Pe, sparseness=pcon) print 'Saving' See1.save_connectivity('./See1_connections_std_saver_p20_' + str(run_num)) See2.save_connectivity('./See2_connections_std_saver_p20_' + str(run_num)) Sie1.save_connectivity('./Sie1_connections_std_saver_p20_' + str(run_num)) Sie2.save_connectivity('./Sie2_connections_std_saver_p20_' + str(run_num)) Sii.save_connectivity('./Sii_connections_std_saver_p20_' + str(run_num)) Sei.save_connectivity('./Sei_connections_std_saver_p20_' + str(run_num)) Seo.save_connectivity('./Seo_connections_std_saver_p20_' + str(run_num)) else: print 'Loading' See1.load_connectivity('./See1_connections_std_saver_p20_' + str(run_num)) See2.load_connectivity('./See2_connections_std_saver_p20_' + str(run_num)) Sie1.load_connectivity('./Sie1_connections_std_saver_p20_' + str(run_num)) Sie2.load_connectivity('./Sie2_connections_std_saver_p20_' + str(run_num)) Sii.load_connectivity('./Sii_connections_std_saver_p20_' + str(run_num)) Sei.load_connectivity('./Sei_connections_std_saver_p20_' + str(run_num)) Seo.load_connectivity('./Seo_connections_std_saver_p20_' + str(run_num)) See1.we_ampa1 = SEE1 * 1.0 * bn.mV / tee_ampa See1.we_nmda1 = SEE1 * 1.0 * bn.mV / tee_nmda See1.we_ampa2 = 0.0 * bn.mV / tee_ampa See1.we_nmda2 = 0.0 * bn.mV / tee_nmda See2.we_ampa1 = 0.0 * bn.mV / tee_ampa See2.we_nmda1 = 0.0 * bn.mV / tee_nmda See2.we_ampa2 = SEE2 * 1.0 * bn.mV / tee_ampa See2.we_nmda2 = SEE2 * 1.0 * bn.mV / tee_nmda Sie1.we_ampa1 = 0.0 * bn.mV / tie_ampa Sie1.we_nmda1 = 0.0 * bn.mV / tie_nmda Sie1.we_ampa2 = SEE1 * 1.0 * bn.mV / tie_ampa Sie1.we_nmda2 = SEE1 * 1.0 * bn.mV / tie_nmda Sie2.we_ampa1 = SEE2 * 1.0 * bn.mV / tie_ampa Sie2.we_nmda1 = SEE2 * 1.0 * bn.mV / tie_nmda Sie2.we_ampa2 = 0.0 * bn.mV / tie_ampa Sie2.we_nmda2 = 0.0 * bn.mV / tie_nmda Sei.wi_gaba = 1.0 * bn.mV / tei_gaba Sii.wi_gaba = 1.0 * bn.mV / tii_gaba Seo.wo_input = 1.0 * bn.mV / teo_input #============================================================================== # Define monitors #============================================================================== Pe_mon_V = bn.StateMonitor(Pe, 'V', timestep=10, record=True) Pe_mon_eta = bn.StateMonitor(Pe, 'eta', timestep=1, record=True) Pe_mon_ampa1 = bn.StateMonitor(Pe, 'I_ampa1', timestep=1, record=True) Pe_mon_nmda1 = bn.StateMonitor(Pe, 'I_nmda1', timestep=1, record=True) Pe_mon_ampa2 = bn.StateMonitor(Pe, 'I_ampa2', timestep=1, record=True) Pe_mon_nmda2 = bn.StateMonitor(Pe, 'I_nmda2', timestep=1, record=True) Pe_mon_gaba = bn.StateMonitor(Pe, 'I_gaba', timestep=1, record=True) Pe_mon_input = bn.StateMonitor(Pe, 'I_input', timestep=10, record=True) See1_mon_x = bn.StateMonitor(Pe, 'x1', timestep=10, record=True) See2_mon_x = bn.StateMonitor(Pe, 'x2', timestep=10, record=True) Pe_ratemon = bn.PopulationRateMonitor(Pe, bin=10.0 * bn.ms) Pi_ratemon = bn.PopulationRateMonitor(Pi, bin=10.0 * bn.ms) #============================================================================== # Run model #============================================================================== timer = 0 * bn.second t_start = time.time() bn.run(T, report='graphical') timer = timer + T print '-------------------------------------------------------' print 'Time is ' + str(timer) + ' seconds' t_end = time.time() print 'Time to compute last ' +str(T)+' seconds is: ' + \ str(t_end - t_start) + ' seconds' print '-------------------------------------------------------\n' Pe_mon_ampa1_vals = Pe.J_ampa1[0] * np.mean(Pe_mon_ampa1.values.T, axis=1) Pe_mon_nmda1_vals = Pe.J_nmda1[0] * np.mean(Pe_mon_nmda1.values.T, axis=1) Pe_mon_ampa2_vals = Pe.J_ampa2[0] * np.mean(Pe_mon_ampa2.values.T, axis=1) Pe_mon_nmda2_vals = Pe.J_nmda2[0] * np.mean(Pe_mon_nmda2.values.T, axis=1) Pe_mon_ampa_vals = Pe_mon_ampa1_vals + Pe_mon_ampa2_vals Pe_mon_nmda_vals = Pe_mon_nmda1_vals + Pe_mon_nmda2_vals Pe_mon_gaba_vals = Pe.J_gaba[0] * np.mean(Pe_mon_gaba.values.T, axis=1) Pe_mon_input_vals = Pe.J_input[0] * np.mean(Pe_mon_input.values.T, axis=1) Pe_mon_V_vals = np.mean(Pe_mon_V.values.T, axis=1) Pe_mon_all_vals = Pe_mon_ampa_vals + Pe_mon_nmda_vals - Pe_mon_gaba_vals See1_mon_x_vals = np.mean(See1_mon_x.values.T, axis=1) See2_mon_x_vals = np.mean(See2_mon_x.values.T, axis=1) #============================================================================== # Save into a Matlab file #============================================================================== if osc: Pe_output = Pe.J_ampa1[0]*Pe_mon_ampa1.values+Pe.J_nmda1[0]*Pe_mon_nmda1.values + \ Pe.J_ampa2[0]*Pe_mon_ampa2.values+Pe.J_nmda2[0]*Pe_mon_nmda2.values-Pe.J_gaba[0]*Pe_mon_gaba.values Pe_output = Pe_output[:, fft_start:, ] Pe_V = Pe_mon_V.values[:, fft_start:, ] Pe_glut = Pe.J_ampa1[0]*Pe_mon_ampa1.values+Pe.J_nmda1[0]*Pe_mon_nmda1.values + \ Pe.J_ampa2[0]*Pe_mon_ampa2.values+Pe.J_nmda2[0]*Pe_mon_nmda2.values Pe_glut = Pe_glut[:, fft_start:, ] Pe_gaba = Pe.J_gaba[0] * Pe_mon_gaba.values Pe_gaba = Pe_gaba[:, fft_start:, ] Pe_input = Pe_mon_eta[:, fft_start:, ] T_step = bn.defaultclock.dt holder = { 'Pe_output': Pe_output, 'Pe_input': Pe_input, 'Pe_V': Pe_V, 'Pe_glut': Pe_glut, 'Pe_gaba': Pe_gaba, 'T_step': T_step } scipy.io.savemat(fft_file + 'delta_u' + str(delta_u) + '_' + str(rep), mdict=holder) else: holder = { 'Pe_rate': Pe_ratemon.rate, 'Pe_time': Pe_ratemon.times, 'uee1': uee1, 'uee2': uee2, 'uie1': uie1, 'uie2': uie2 } scipy.io.savemat(rate_file + 'delta_q_' + str(delta_u) + '_' + str(run_num) + 'rep' + str(rep), mdict=holder) bn.clear(erase=True, all=True)
def tearDownClass(BrianMonitorTest): clear(True, True) reload(brian)
import random import string import struct from brian import Network, Equations, NeuronGroup, Connection,\ SpikeMonitor, raster_plot, StateMonitor, clear, reinit from brian.stdunits import ms, mV, nS, pA, pF, Hz for i in range(len(sys.argv)): if sys.argv[i] == "-rEE": rEE = float(sys.argv[i+1]) #%matplotlib inline pylab.rcParams['figure.figsize'] = 12, 8 # changes figure size (width, height) for larger images clear(True, True) reinit()# To reinit brain clocks and remove all old brian objects from namespace, # it's usually a good idea to put this at the beginning of a script # The equations defining our neuron model eqs_string = ''' dV/dt = (1.0/tau)*(myu-V) + Isyn : 1 Isyn = Isyne - Isyni : hertz dIsyne/dt = -(1/tau1)*(Isyne + ye) : hertz dye/dt = -(1/tau2)*ye : hertz dIsyni/dt = -(1/tau1)*(Isyni + yi) : hertz dyi/dt = -(1/tau2)*yi : hertz myu : 1 '''
def run_simulation(realizations=1, trials=1, t=3000 * ms, alpha=1, ree=1, k=50, winlen = 50 * ms, verbose=True, t_stim = 0): """ Run the whole simulation with the specified parameters. All model parameter are set in the function. Keyword arguments: :param realizations: number of repititions of the whole simulation, number of network instances :param trials: number of trials for network instance :param t: simulation time :param alpha: scaling factor for number of neurons in the network :param ree: clustering coefficient :param k: number of clusters :param t_stim : duration of stimulation of a subset of clusters :param winlen: length of window in ms :param verbose: plotting flag :return: numpy matrices with spike times """ # The equations defining our neuron model eqs_string = ''' dV/dt = (mu - V)/tau + x: volt dx/dt = -1.0/tau_2*(x - y/tau_1) : volt/second dy/dt = -y/tau_1 : volt mu : volt tau: second tau_2: second tau_1: second ''' # Model parameters n_e = int(4000 * alpha) # number of exc neurons n_i = int(1000 * alpha) # number of inh neurons tau_e = 15 * ms # membrane time constant (for excitatory synapses) tau_i = 10 * ms # membrane time constant (for inhibitory synapses) tau_syn_2_e = 3 * ms # exc synaptic time constant tau2 in paper tau_syn_2_i = 2 * ms # inh synaptic time constant tau2 in paper tau_syn_1 = 1 * ms # exc/inh synaptic time constant tau1 in paper vt = -50 * mV # firing threshold vr = -65 * mV # reset potential dv = vt - vr # delta v refrac = 5 * ms # absolute refractory period # scale the weights to ensure same variance in the inputs wee = 0.024 * dv * np.sqrt(1. / alpha) wie = 0.014 * dv * np.sqrt(1. / alpha) wii = -0.057 * dv * np.sqrt(1. / alpha) wei = -0.045 * dv * np.sqrt(1. / alpha) # Connection probability p_ee = 0.2 p_ii = 0.5 p_ie = 0.5 p_ei = 0.5 # determine probs for inside and outside of clusters p_in, p_out = get_cluster_connection_probs(ree, k, p_ee) mu_min_e, mu_max_e = 1.1, 1.2 mu_min_i, mu_max_i = 1.0, 1.05 # increase cluster weights if there are clusters wee_cluster = wee if p_in == p_out else 1.9 * wee # define numpy array for data storing all_data = np.zeros((realizations, trials, n_e+n_i, int(t/winlen)//2)) for realization in range(realizations): # clear workspace to make sure that is a new realization of the network clear(True, True) reinit() # set up new random bias parameter for every type of neuron mu_e = vr + np.random.uniform(mu_min_e, mu_max_e, n_e) * dv # bias for excitatory neurons mu_i = vr + np.random.uniform(mu_min_i, mu_max_i, n_i) * dv # bias for excitatory neurons # Let's create an equation object from our string and parameters model_eqs = Equations(eqs_string) # Let's create 5000 neurons all_neurons = NeuronGroup(N=n_e + n_i, model=model_eqs, threshold=vt, reset=vr, refractory=refrac, freeze=True, method='Euler', compile=True) # Divide the neurons into excitatory and inhibitory ones neurons_e = all_neurons[0:n_e] neurons_i = all_neurons[n_e:n_e + n_i] # set the bias neurons_e.mu = mu_e neurons_i.mu = mu_i neurons_e.tau = tau_e neurons_i.tau = tau_i neurons_e.tau_2 = tau_syn_2_e neurons_i.tau_2 = tau_syn_2_i all_neurons.tau_1 = tau_syn_1 # set up connections connections = Connection(all_neurons, all_neurons, 'y') # do the cluster connection like cross validation: cluster neuron := test idx; other neurons := train idx kf = KFold(n=n_e, n_folds=k) for idx_out, idx_in in kf: # idx_out holds all other neurons; idx_in holds all cluster neurons # connect current cluster to itself connections.connect_random(all_neurons[idx_in[0]:idx_in[-1]], all_neurons[idx_in[0]:idx_in[-1]], sparseness=p_in, weight=wee_cluster) # connect current cluster to other neurons connections.connect_random(all_neurons[idx_in[0]:idx_in[-1]], all_neurons[idx_out[0]:idx_out[-1]], sparseness=p_out, weight=wee) # connect all excitatory to all inhibitory, irrespective of clustering connections.connect_random(all_neurons[0:n_e], all_neurons[n_e:(n_e + n_i)], sparseness=p_ie, weight=wie) # connect all inhibitory to all excitatory connections.connect_random(all_neurons[n_e:(n_e + n_i)], all_neurons[0:n_e], sparseness=p_ei, weight=wei) # connect all inhibitory to all inhibitory connections.connect_random(all_neurons[n_e:(n_e + n_i)], all_neurons[n_e:(n_e + n_i)], sparseness=p_ii, weight=wii) # set up spike monitors spike_mon_e = SpikeMonitor(neurons_e) spike_mon_i = SpikeMonitor(neurons_i) # set up network with monitors network = Network(all_neurons, connections, spike_mon_e, spike_mon_i) # run this network for some number of trials, every time with for trial in range(trials): # different initial values all_neurons.V = vr + (vt - vr) * np.random.rand(len(all_neurons)) * 1.4 # Calibration phase # run for the first half of the time to let the neurons adapt network.run(t/2) # reset monitors to start recording phase spike_mon_i.reinit() spike_mon_e.reinit() # stimulation if duration is given # define index variable for the stimulation possibility (is 0 for stimulation time=0) t_stim_idx = int(t_stim / (winlen/ms)) if not(t_stim==0): # Stimulation phase, increase input to subset of clusters all_neurons[:400].mu += 0.07 * dv network.run(t_stim * ms, report='text') # set back to normal all_neurons[:400].mu -= 0.07 * dv # save data all_data[realization, trial, :n_e, :t_stim_idx] = spikes_counter(spike_mon_e, winlen) all_data[realization, trial, n_e:, :t_stim_idx] = spikes_counter(spike_mon_i, winlen) # reset monitors spike_mon_e.reinit() spike_mon_i.reinit() # run the remaining time of the simulation network.run((t/2) - t_stim*ms, report='text') # save results all_data[realization, trial, :n_e, t_stim_idx:] = spikes_counter(spike_mon_e, winlen) all_data[realization, trial, n_e:, t_stim_idx:] = spikes_counter(spike_mon_i, winlen) if verbose: plt.ion() plt.figure() raster_plot(spike_mon_e) plt.title('Excitatory neurons') spike_mon_e.reinit() spike_mon_i.reinit() return all_data