Exemplo n.º 1
0
def connect_timetable(post_connection,syncomps,totalsyn,netparams,model):
    dist=0
    syn_params=model.param_syn
    simdt=model.param_sim.simdt
    #tt_list is list of time tables stored with number of times the time table can be used in the network
    tt_list=post_connection.pre.stimtab
    dend_loc=post_connection.dend_loc
    if getattr(model,'stpYN',False):
        stp=post_connection.stp
    else:
        stp=None
    connections={}
    num_choices=np.int(np.round(totalsyn))
    if num_choices>0:
        #randomly select num_choices of synapses without replacement from the entire set
        syn_choices=np.random.choice([sc[0] for sc in syncomps],size=num_choices,replace=False,p=[sc[1] for sc in syncomps])
        #randomly select subset of time-tables for spike train input
        presyn_tt=[select_entry(tt_list) for syn in syn_choices]
        print('## connect from tt',post_connection.pre.tablename)
    else:
        syn_choices=[];presyn_tt=[]
        print('&& no connectons from time tables',post_connection.pre.tablename)
    #connect the time-table to the synapse with mindelay (set dist=0)
    for tt,syn in zip(presyn_tt,syn_choices):
        postbranch=util.syn_name(moose.element(syn).parent.path,NAME_HEAD)
        log.info('CONNECT: TT {} POST {} {}', tt,syn, postbranch)
        synconn(syn,dist,tt,syn_params,netparams.mindelay,simdt=simdt,stp=stp,weight=post_connection.weight)
        #save the connection in a dictionary for inspection later
        connections[postbranch]=tt.path
    return connections
Exemplo n.º 2
0
def connect_timetable(post_connection, syncomps, totalsyn, model, mindelay=0):
    dist = 0
    syn_params = model.param_syn
    simdt = model.param_sim.simdt
    #tt_list is list of time tables stored with number of times the time table can be used in the network
    tt_list = post_connection.pre.stimtab
    dend_loc = post_connection.dend_loc
    if getattr(model, 'stpYN', False):
        stp = post_connection.stp
    else:
        stp = None
    connections = {}
    num_choices = np.int(np.round(totalsyn))
    if num_choices > 0:
        #randomly select num_choices of synapses without replacement from the entire set
        syn_choices = np.random.choice([sc[0] for sc in syncomps],
                                       size=num_choices,
                                       replace=False,
                                       p=[sc[1] for sc in syncomps])
        #randomly select subset of time-tables for spike train input
        #could do this in one line, but then meaningless error message
        log.info('>>>>>>>>> num_choices {} for {} {} tt remaining {} from',
                 num_choices, post_connection.post, post_connection.synapse,
                 len(tt_list), post_connection.pre.tablename)
        if len(tt_list) < 1000:  #2*num_choices:
            print('>>>>>>>>> num_choices {} for {} {} tt remaining {} from'.
                  format(num_choices,
                         post_connection.post, post_connection.synapse,
                         len(tt_list), post_connection.pre.tablename))
        presyn_tt = []
        for i, syn in enumerate(syn_choices):
            if len(tt_list) > 0:
                presyn_tt.append(select_entry(tt_list))
            else:
                print('table empty', i, syn, tt_list)
        #presyn_tt=[select_entry(tt_list) for syn in syn_choices]
    else:
        syn_choices = []
        presyn_tt = []
        log.info('&&&&&&&&&&&&&& no connectons from time tables'.format(
            post_connection.pre.tablename))
    #connect the time-table to the synapse with mindelay (set dist=0)
    for tt, syn in zip(presyn_tt, syn_choices):
        postbranch = util.syn_name(moose.element(syn).parent.path, NAME_HEAD)
        log.debug('CONNECT: TT {} POST {}', tt.path, syn)
        synconn(syn,
                dist,
                tt,
                syn_params,
                mindelay,
                simdt=simdt,
                stp=stp,
                weight=post_connection.weight)
        #save the connection in a dictionary for inspection later.
        if postbranch in connections.keys():
            connections[postbranch].append(tt.path)
        else:
            connections[postbranch] = [tt.path]
    return connections
Exemplo n.º 3
0
def HookUpDend(model, dendrite, container):

    #for dend in model.Stimulation.StimParams.which_dendrites:
    my_spines = list(
        set(moose.element(dendrite).neighbors['handleAxial']).intersection(
            set(moose.element(dendrite).children)))
    spine_no = len(my_spines)

    if not spine_no:
        return

    synapses = {}
    for spine in my_spines:
        spine_no = int(''.join(c for c in spine.name if c.isdigit()))
        synapses[spine_no] = []
        heads = moose.element(spine).neighbors['handleAxial']
        for head in heads:
            moose_head = moose.element(head)
            for child in moose_head.children:
                moose_child = moose.element(child)
                if moose_child.className == 'SynChan' or moose_child.className == 'NMDAChan':
                    synapses[spine_no].append(moose_child)

    time_tables = MakeTimeTables(model.Stimulation, spine_no)
    stimtab = {}

    stim_synapses = {}

    for spine in time_tables:
        stimtab[spine] = moose.TimeTable(
            '%s/TimTab%s_%s' % (container.path, dendrite.name, str(spine)))
        stimtab[spine].vector = np.array(time_tables[spine])

        for synapse in synapses[spine]:
            synchan = moose.element(synapse)
            print(synapse.path, time_tables[spine])
            connect.plain_synconn(synchan, stimtab[spine], 0)
            synname = util.syn_name(synchan.path, spines.NAME_HEAD)

            if model.desenYN and model.DesensitizationParams[synchan.name]:
                dep, weight = plasticity.desensitization(
                    synchan, model.DesensitizationParams[synchan.name])

                stim_synapses[synname] = {}
                stim_synapses[synname]['plas'] = dep
                stim_synapses[synname]['cum'] = weight
                stim_synapses[synname]['syn'] = synchan
                synchan.Gbar = synchan.Gbar / 2

    return stim_synapses
Exemplo n.º 4
0
def connect_timetable(post_connection, syncomps, totalsyn, netparams,
                      syn_params):
    dist = 0
    tt_list = post_connection.pre.stimtab
    postsyn_fraction = post_connection.postsyn_fraction
    num_tt = len(tt_list)
    connections = {}
    #calculate how many of these timetables should be connected to this synapse type
    #randomly select a timetable (presyn_tt), and post-synaptic branch (synpath) for each connection
    for i in range(np.int(np.round(totalsyn * postsyn_fraction))):
        presyn_tt = select_entry(tt_list)
        synpath = select_entry(syncomps)
        log.debug('CONNECT: TT {} POST {} ', presyn_tt.path, synpath)
        #connect the time table with mindelay (dist=0)
        synconn(synpath, dist, presyn_tt, syn_params, netparams.mindelay)
        postbranch = util.syn_name(synpath, NAME_HEAD)
        connections[postbranch] = presyn_tt.path
    return connections
Exemplo n.º 5
0
def addPlasticity(cell_pop, caplas_params):
    log.info("{} ", cell_pop)
    plascum = {}

    for cell in cell_pop:

        plascum[cell] = {}
        allsyncomp_list = moose.wildcardFind(cell + '/##/' +
                                             caplas_params.Plas_syn.Name +
                                             '[ISA=SynChan]')

        for synchan in allsyncomp_list:
            #if synapse exists
            if moose.exists(synchan.path + '/SH'):
                log.debug("{} {} {}", cell, synchan.path,
                          moose.element(synchan.path + '/SH'))
                synname = util.syn_name(synchan.path, spines.NAME_HEAD)
                plascum[cell][synname] = plasticity2(synchan,
                                                     caplas_params.Plas_syn)

    return plascum
Exemplo n.º 6
0
def connect_neurons(cells, netparams, postype, model):
    log.info('CONNECT set: {} {} {}', postype, cells[postype],
             netparams.connect_dict[postype])
    post_connections = netparams.connect_dict[postype]
    connect_list = {pc: {} for pc in cells[postype]}
    intra_conns = {
        key: []
        for key in post_connections.keys()
    }  # accumulate number of connections of each type to calculate mean
    # loop over post-synaptic neurons - convert to list if only singe instance of any type
    if not isinstance(cells[postype], list):
        temp = cells[postype]
        cells[postype] = list([temp])
    for postcell in cells[postype]:
        postsoma = postcell + '/' + model.param_cond.NAME_SOMA
        xpost = moose.element(postsoma).x
        ypost = moose.element(postsoma).y
        zpost = moose.element(postsoma).z
        connect_list[postcell]['postsoma_loc'] = (xpost, ypost, zpost)
        # set-up array of post-synapse compartments/synchans
        for syntype in post_connections.keys():
            connect_list[postcell][syntype] = {}
            # make a table of possible post-synaptic connections
            for pretype in post_connections[syntype].keys():
                dend_prob = post_connections[syntype][pretype].dend_loc
                allsyncomp_list = moose.wildcardFind(postcell + '/##/' +
                                                     syntype + '[ISA=SynChan]')
                print('CREATE_SYNPATH_ARRAY from connect_neurons, pre=',
                      pretype)
                syncomps, totalsyn, availsyns = create_synpath_array(
                    allsyncomp_list,
                    syntype,
                    model.param_syn.NumSyn,
                    prob=dend_prob)
                log.info(
                    'SYN TABLE for {} {} {} has {} compartments and {} synapses',
                    postsoma, syntype, pretype, len(syncomps), totalsyn)
                if 'extern' in pretype:
                    print('## connect to tt', postcell, syntype, pretype)
                    ####### connect to time tables instead of other neurons in network
                    connect_list[postcell][syntype][
                        pretype] = connect_timetable(
                            post_connections[syntype][pretype], syncomps,
                            totalsyn, netparams, model)
                    intra_conns[syntype].append(
                        len(connect_list[postcell][syntype][pretype]))
                else:
                    if getattr(model, 'stpYN', False):
                        stp = post_connections[syntype][pretype].stp
                    else:
                        stp = None
                    spikegen_conns = []
                    fact = 1
                    prob = 0
                    ###### connect to other neurons in network: loop over pre-synaptic neurons
                    for precell in cells[pretype]:
                        presoma = precell + '/' + model.param_cond.NAME_SOMA
                        xpre = moose.element(presoma).x
                        ypre = moose.element(presoma).y
                        zpre = moose.element(presoma).z
                        dist = np.sqrt((xpre - xpost)**2 + (ypre - ypost)**2 +
                                       (zpre - zpost)**2)
                        if post_connections[syntype][pretype].space_const:
                            fact = post_connections[syntype][
                                pretype].space_const
                            # calculate distance between pre- and post-soma
                            prob = np.exp(-(dist / fact))
                        elif post_connections[syntype][pretype].probability:
                            prob = post_connections[syntype][
                                pretype].probability
                        else:
                            print(
                                'need to specify either probability or space constant in param_net for',
                                syntype, pretype)
                        connect = np.random.uniform()
                        log.debug('{} {} {} {} {} {}', presoma, postsoma, dist,
                                  fact, prob, connect)
                        # select a random number to determine whether a connection should occur
                        if connect < prob and dist > 0:
                            spikegen_conns.append([
                                moose.wildcardFind(presoma +
                                                   '/#[TYPE=SpikeGen]')[0],
                                (xpre, ypre, zpre), dist
                            ])
                    if len(spikegen_conns):
                        num_conn = [
                            max(
                                np.random.poisson(post_connections[syntype]
                                                  [pretype].num_conns), 1)
                            for n in spikegen_conns
                        ]
                        print('&& connect to neuron', postcell, syntype,
                              'from', pretype, 'num conns', num_conn)
                        intra_conns[syntype].append(np.sum(num_conn))
                        # duplicate spikegens in list to match the length of the list syn_choices to be generated
                        for i in range(len(num_conn) - 1, -1, -1):
                            for n in range(num_conn[i] - 1):
                                spikegen_conns.insert(i, spikegen_conns[i])
                        num_choices = min(len(spikegen_conns), availsyns)
                        if len(spikegen_conns) > availsyns:
                            print(
                                '>>>> uh oh, too few synapses on post-synaptic cell'
                            )
                        # randomly select num_choices of synapses
                        if availsyns == 0:
                            print(
                                '>>>>>>>>>>> uh oh, no available synapses on post-synaptic cell'
                            )
                            syn_choices = []
                        else:
                            syn_choices = np.random.choice(
                                [sc[0] for sc in syncomps],
                                size=num_choices,
                                replace=False,
                                p=[sc[1] for sc in syncomps])
                        log.debug('CONNECT: PRE {} POST {} ', spikegen_conns,
                                  syn_choices)
                        # connect the pre-synaptic spikegens to randomly chosen synapses
                        for i, syn in enumerate(syn_choices):
                            postbranch = util.syn_name(
                                moose.element(syn).parent.path, NAME_HEAD)
                            precell = spikegen_conns[i][0].parent.path.split(
                                '/')[2].split('[')[0]
                            connect_list[postcell][syntype][
                                precell + CONNECT_SEPARATOR + postbranch] = {
                                    'presoma_loc': spikegen_conns[i][1],
                                    'dist': np.round(spikegen_conns[i][2], 6)
                                }
                            log.debug('{}', connect_list[postcell][syntype])
                            # connect the synapse
                            # print('** intrinsic synconn',i,syn,spikegen_conns[i][2],spikegen_conns[i][0].path)
                            synconn(syn,
                                    spikegen_conns[i][2],
                                    spikegen_conns[i][0],
                                    model.param_syn,
                                    netparams.mindelay,
                                    netparams.cond_vel,
                                    stp_params=stp)
                    else:
                        print('   no pre-synaptic cells selected for',
                              postcell, 'from', pretype)
    tmp = [
        np.mean(intra_conns[syn]) / len(cells[postype])
        for syn in intra_conns.keys()
    ]
    print('mean number of intra-network connections', intra_conns, tmp)
    return connect_list
Exemplo n.º 7
0
def connect_neurons(cells, netparams, postype, model):
    log.info('CONNECT set: {} {} {}', postype, cells[postype],netparams.connect_dict[postype])
    post_connections=netparams.connect_dict[postype]
    connect_list = {pc:{} for pc in cells[postype]}
    intra_conns={key:[] for key in post_connections.keys()} #accumulate number of connections of each type to calculate mean
    #loop over post-synaptic neurons - convert to list if only singe instance of any type
    if not isinstance(cells[postype],list):
        temp=cells[postype]
        cells[postype]=list([temp])
    for postcell in cells[postype]:
        postsoma=postcell+'/'+model.param_cond.NAME_SOMA
        xpost=moose.element(postsoma).x
        ypost=moose.element(postsoma).y
        zpost=moose.element(postsoma).z
        connect_list[postcell]['postsoma_loc']=(xpost,ypost,zpost)
        #set-up array of post-synapse compartments/synchans
        for syntype in post_connections.keys():
            connect_list[postcell][syntype]={}
            #make a table of possible post-synaptic connections
            for pretype in post_connections[syntype].keys():
                dend_prob=post_connections[syntype][pretype].dend_loc
                allsyncomp_list=moose.wildcardFind(postcell+'/##/'+syntype+'[ISA=SynChan]')
                print('CREATE_SYNPATH_ARRAY from connect_neurons, pre=', pretype)
                syncomps,totalsyn,availsyns=create_synpath_array(allsyncomp_list,syntype,model.param_syn.NumSyn,prob=dend_prob)
                log.info('SYN TABLE for {} {} {} has {} compartments and {} synapses', postsoma, syntype, pretype,len(syncomps),totalsyn)
                if 'extern' in pretype:
                    print('## connect to tt',postcell,syntype,pretype)
                    ####### connect to time tables instead of other neurons in network
                    connect_list[postcell][syntype][pretype]=connect_timetable(post_connections[syntype][pretype],syncomps,totalsyn,netparams,model.param_syn,model.param_sim.simdt)
                    intra_conns[syntype].append(len(connect_list[postcell][syntype][pretype]))
                else:
                    if getattr(model,'stpYN',False):
                        stp=post_connections[syntype][pretype].stp
                    else:
                        stp=None
                    spikegen_conns=[]
                    fact=1;prob=0
                    ###### connect to other neurons in network: loop over pre-synaptic neurons
                    for precell in cells[pretype]:
                        presoma=precell+'/'+model.param_cond.NAME_SOMA
                        xpre=moose.element(presoma).x
                        ypre=moose.element(presoma).y
                        zpre=moose.element(presoma).z
                        dist=np.sqrt((xpre-xpost)**2+(ypre-ypost)**2+(zpre-zpost)**2)
                        if post_connections[syntype][pretype].space_const:
                            fact=post_connections[syntype][pretype].space_const
                            #calculate distance between pre- and post-soma
                            prob=np.exp(-(dist/fact))
                        elif post_connections[syntype][pretype].probability:
                            prob=post_connections[syntype][pretype].probability
                        else:
                            print('need to specify either probability or space constant in param_net for', syntype,pretype)
                        connect=np.random.uniform()
                        log.debug('{} {} {} {} {} {}', presoma,postsoma,dist,fact,prob,connect)
                        #select a random number to determine whether a connection should occur
                        if connect<prob and dist>0:
                            spikegen_conns.append([moose.wildcardFind(presoma+'/#[TYPE=SpikeGen]')[0],(xpre,ypre,zpre),dist])
                    if len(spikegen_conns):
                        num_conn=[max(np.random.poisson(post_connections[syntype][pretype].num_conns),1) for n in spikegen_conns]
                        print('&& connect to neuron', postcell,syntype,'from',pretype,'num conns',num_conn)
                        intra_conns[syntype].append(np.sum(num_conn))
                        #duplicate spikegens in list to match the length of the list syn_choices to be generated
                        for i in range(len(num_conn)-1,-1,-1):
                            for n in range(num_conn[i]-1):
                                spikegen_conns.insert(i,spikegen_conns[i])
                        num_choices=min(len(spikegen_conns),availsyns)
                        if len(spikegen_conns)>availsyns:
                            print('>>>> uh oh, too few synapses on post-synaptic cell')
                        #randomly select num_choices of synapses
                        if availsyns==0:
                            print('>>>>>>>>>>> uh oh, no available synapses on post-synaptic cell')
                            syn_choices=[]
                        else:
                            syn_choices=np.random.choice([sc[0] for sc in syncomps],size=num_choices,replace=False,p=[sc[1] for sc in syncomps])
                        log.debug('CONNECT: PRE {} POST {} ', spikegen_conns,syn_choices)
                        #connect the pre-synaptic spikegens to randomly chosen synapses
                        for i,syn in enumerate(syn_choices):
                                postbranch=util.syn_name(moose.element(syn).parent.path,NAME_HEAD)
                                precell=spikegen_conns[i][0].parent.path.split('/')[2].split('[')[0]
                                connect_list[postcell][syntype][precell+CONNECT_SEPARATOR+postbranch]={'presoma_loc':spikegen_conns[i][1],'dist':np.round(spikegen_conns[i][2],6)}
                                log.debug('{}',connect_list[postcell][syntype])
                                #connect the synapse
                                #print('** intrinsic synconn',i,syn,spikegen_conns[i][2],spikegen_conns[i][0].path)
                                synconn(syn,spikegen_conns[i][2], spikegen_conns[i][0],model.param_syn,netparams.mindelay,netparams.cond_vel,stp_params=stp)
                    else:
                        print('   no pre-synaptic cells selected for',postcell, 'from',pretype)
    tmp=[np.mean(intra_conns[syn])/len(cells[postype]) for syn in intra_conns.keys()]                                     
    print('mean number of intra-network connections', intra_conns,tmp)
    return connect_list
Exemplo n.º 8
0
def connect_neurons(cells, netparams, postype, model):
    log.debug('CONNECT set: {} {} {}', postype, cells[postype],
              netparams.connect_dict[postype])
    post_connections = netparams.connect_dict[postype]
    connect_list = {}
    #loop over post-synaptic neurons - convert to list if only singe instance of any type
    if not isinstance(cells[postype], list):
        temp = cells[postype]
        cells[postype] = list([temp])
    for postcell in cells[postype]:
        connect_list[postcell] = {}
        postsoma = postcell + '/' + model.param_cond.NAME_SOMA
        xpost = moose.element(postsoma).x
        ypost = moose.element(postsoma).y
        zpost = moose.element(postsoma).z
        #set-up array of post-synapse compartments/synchans
        for syntype in post_connections.keys():
            allsyncomp_list = moose.wildcardFind(postcell + '/##/' + syntype +
                                                 '[ISA=SynChan]')
            connect_list[postcell][syntype] = {}
            #make a table of possible post-synaptic connections
            syncomps, totalsyn = create_synpath_array(allsyncomp_list, syntype,
                                                      model.param_syn.NumSyn)
            log.debug(
                'SYN TABLE for {} {} has {} compartments and {} synapses',
                postsoma, syntype, len(syncomps), totalsyn)
            for pretype in post_connections[syntype].keys():
                if 'extern' in pretype:
                    ####### connect to time tables instead of other neurons in network
                    connect_list[postcell][syntype] = connect_timetable(
                        post_connections[syntype][pretype], syncomps, totalsyn,
                        netparams, model.param_syn)
                else:
                    ###### connect to other neurons in network: loop over pre-synaptic neurons
                    for precell in cells[pretype]:
                        presoma = precell + '/' + model.param_cond.NAME_SOMA
                        fact = post_connections[syntype][pretype].space_const
                        xpre = moose.element(presoma).x
                        ypre = moose.element(presoma).y
                        zpre = moose.element(presoma).z
                        #calculate distance between pre- and post-soma
                        dist = np.sqrt((xpre - xpost)**2 + (ypre - ypost)**2 +
                                       (zpre - zpost)**2)
                        prob = np.exp(-(dist / fact))
                        connect = np.random.uniform()
                        log.debug('{} {} {} {} {} {}', presoma, postsoma, dist,
                                  fact, prob, connect)
                        #select a random number to determine whether a connection should occurmore c
                        if connect < prob and dist > 0 and len(syncomps) > 0:
                            spikegen = moose.wildcardFind(
                                presoma + '/#[TYPE=SpikeGen]')[0]
                            #if so, randomly select a branch, and then eliminate that branch from the table.
                            #presently only a single synapse established.  Need to expand this to allow multiple conns
                            synpath = select_entry(syncomps)
                            log.debug('CONNECT: PRE {} POST {} DIST {}',
                                      spikegen, synpath, dist)
                            #list of connections for further processing if desired.  Assumes one conn per synpath (which might be a problem)
                            postbranch = util.syn_name(synpath, NAME_HEAD)
                            connect_list[postcell][syntype][postbranch] = {
                                'postloc': (xpost, ypost, zpost),
                                'pre': precell,
                                'preloc': (xpre, ypre, zpre),
                                'dist': dist,
                                'prob': prob
                            }
                            log.debug('{}', connect_list[postcell][syntype])
                            #connect the synapse
                            synconn(synpath, dist, spikegen, model.param_syn,
                                    netparams.mindelay, netparams.cond_vel)
    return connect_list
Exemplo n.º 9
0
def connect_neurons(cells, netparams, postype, model):
    print_cells = 3
    print('CONNECT_NEURONS, num cells', len(cells[postype]), ', a few cells',
          [cl for cl in cells[postype][0:print_cells]])
    log.info('CONNECT set: {} {} {}', postype, cells[postype],
             netparams.connect_dict[postype])
    post_connections = netparams.connect_dict[postype]
    connect_list = {pc: {} for pc in cells[postype]}
    intra_conns = {
        key: {k: []
              for k in post_connections[key].keys()}
        for key in post_connections.keys()
    }  #accumulate number of connections of each type to calculate mean
    #loop over post-synaptic neurons - convert to list if only singe instance of any type
    if not isinstance(cells[postype], list):
        temp = cells[postype]
        cells[postype] = list([temp])
    synchan_shortage = {k: {} for k in post_connections.keys()}
    for ix, postcell in enumerate(cells[postype]):
        postsoma = postcell + '/' + model.param_cond.NAME_SOMA
        xpost = moose.element(postsoma).x
        ypost = moose.element(postsoma).y
        zpost = moose.element(postsoma).z
        connect_list[postcell]['postsoma_loc'] = (xpost, ypost, zpost)
        #set-up array of post-synapse compartments/synchans
        for syntype in post_connections.keys():
            synchan_shortage[syntype][postcell] = 0
            connect_list[postcell][syntype] = {}
            #make a table of possible post-synaptic connections
            for pretype in post_connections[syntype].keys():
                dend_prob = post_connections[syntype][pretype].dend_loc
                allsyncomp_list = moose.wildcardFind(postcell + '/##/' +
                                                     syntype + '[ISA=SynChan]')
                syncomps, totalsyn, availsyns = create_synpath_array(
                    allsyncomp_list,
                    syntype,
                    model.param_syn.NumSyn[postype],
                    prob=dend_prob,
                    soma_loc=[xpost, ypost, zpost])
                if ix < print_cells:
                    print(
                        '    SYN TABLE for {} {} from {} has {} slots and {} synapses avail'
                        .format(postsoma, syntype, pretype, len(syncomps),
                                availsyns))
                if 'extern' in pretype:
                    if ix < print_cells:
                        print('## connect to tt', postcell, syntype, pretype,
                              'from',
                              post_connections[syntype][pretype].pre.filename)
                    ####### connect to time tables instead of other neurons in network
                    connect_list[postcell][syntype][
                        pretype] = connect_timetable(
                            post_connections[syntype][pretype], syncomps,
                            totalsyn, model)
                    intra_conns[syntype][pretype].append(
                        np.sum([
                            len(item) for item in connect_list[postcell]
                            [syntype][pretype].values()
                        ]))
                else:
                    if getattr(model, 'stpYN', False):
                        stp = post_connections[syntype][pretype].stp
                    else:
                        stp = None
                    spikegen_conns = []
                    fact = 1
                    prob = 0
                    ###### connect to other neurons in network: loop over pre-synaptic neurons
                    for precell in cells[pretype]:
                        presoma = precell + '/' + model.param_cond.NAME_SOMA
                        xpre = moose.element(presoma).x
                        ypre = moose.element(presoma).y
                        zpre = moose.element(presoma).z
                        dist = np.sqrt((xpre - xpost)**2 + (ypre - ypost)**2 +
                                       (zpre - zpost)**2)
                        if post_connections[syntype][pretype].space_const:
                            fact = post_connections[syntype][
                                pretype].space_const
                            #calculate distance between pre- and post-soma
                            prob = np.exp(-(dist / fact))
                        elif post_connections[syntype][pretype].probability:
                            prob = post_connections[syntype][
                                pretype].probability
                        else:
                            print(
                                'need to specify either probability or space constant in param_net for',
                                syntype, pretype)
                        connect = np.random.uniform()
                        log.debug('{} {} {} {} {} {}', presoma, postsoma, dist,
                                  fact, prob, connect)
                        #select a random number to determine whether a connection should occur
                        if connect < prob and dist > 0:
                            spikegen_conns.append([
                                moose.wildcardFind(presoma +
                                                   '/#[TYPE=SpikeGen]')[0],
                                (xpre, ypre, zpre), dist
                            ])
                    if len(spikegen_conns):
                        num_conn = [
                            max(
                                np.random.poisson(post_connections[syntype]
                                                  [pretype].num_conns), 1)
                            for n in spikegen_conns
                        ]
                        if ix < print_cells:
                            print('&& connect to neuron', postcell, syntype,
                                  'from', pretype, 'num conns', num_conn)
                        intra_conns[syntype][pretype].append(np.sum(num_conn))
                        #duplicate spikegens in list to match the length of the list syn_choices to be generated
                        for i in range(len(num_conn) - 1, -1, -1):
                            for n in range(num_conn[i] - 1):
                                spikegen_conns.insert(i, spikegen_conns[i])
                        num_choices = min(len(spikegen_conns), availsyns)
                        if len(spikegen_conns) > availsyns:
                            if ix < print_cells:
                                print(
                                    '$$$$$$ uh oh, too few synapses on post-synaptic cell, need',
                                    len(spikegen_conns), ', avail', availsyns)
                            synchan_shortage[syntype][
                                postcell] = synchan_shortage[syntype][
                                    postcell] + len(spikegen_conns) - availsyns
                        #randomly select num_choices of synapses
                        if availsyns == 0:
                            if ix < print_cells:
                                print(
                                    '$$$$$$$$$$$$$$$$ even worse, no available synapses on post-synaptic cell'
                                )
                            syn_choices = []
                        else:
                            syn_choices = np.random.choice(
                                [sc[0] for sc in syncomps],
                                size=num_choices,
                                replace=False,
                                p=[sc[1] for sc in syncomps])
                        log.debug('CONNECT: PRE {} POST {} ', spikegen_conns,
                                  syn_choices)
                        #connect the pre-synaptic spikegens to randomly chosen synapses
                        #print('** intrinsic synconns',pretype, 'one mindelay',netparams.mindelay[pretype],'all cond',netparams.cond_vel, 'num cons:',len(syn_choices))
                        for i, syn in enumerate(syn_choices):
                            postbranch = util.syn_name(
                                moose.element(syn).parent.path, NAME_HEAD)
                            precell = spikegen_conns[i][0].parent.path.split(
                                '/')[2].split('[')[0]
                            connect_list[postcell][syntype][
                                precell + CONNECT_SEPARATOR + postbranch] = {
                                    'presoma_loc': spikegen_conns[i][1],
                                    'dist': np.round(spikegen_conns[i][2], 6)
                                }
                            log.debug('{}', connect_list[postcell][syntype])
                            #connect the synapse
                            #print('** intrinsic synconn',i,syn,spikegen_conns[i][2],spikegen_conns[i][0].path)
                            synconn(syn,
                                    spikegen_conns[i][2],
                                    spikegen_conns[i][0],
                                    model.param_syn,
                                    netparams.mindelay[pretype],
                                    netparams.cond_vel[pretype],
                                    stp=stp,
                                    weight=post_connections[syntype]
                                    [pretype].weight)
                    else:
                        intra_conns[syntype][pretype].append(0)
                        if len(cells[pretype]):
                            print('   !!! no pre-synaptic cells selected for',
                                  postcell, 'from', pretype, 'connect=',
                                  connect, '>? prob=', prob, 'or dist=0?',
                                  dist)
                        else:
                            print('   !!! no pre-synaptic cells selected for',
                                  postcell, ' because no', pretype,
                                  'in population')
    for syn in intra_conns.keys():
        tmp = [(pre,
                np.sum(intra_conns[syn][pre]) / float(len(cells[postype])))
               for pre in intra_conns[syn].keys()]
        print('*************** number of intra-network connections to',
              postype, syn, 'from\n', intra_conns[syn], '\nmean', tmp)
    print('@@@@@@@@@@@@@@@@@@ summary of synchan shortage for', postype)
    for syn, syn_short in synchan_shortage.items():
        if np.sum(list(syn_short.values())) > 0:
            print(syn, ':::', [short for short in syn_short.values()], 'mean',
                  np.mean([short for short in syn_short.values()]))
        else:
            print(syn, '::: shortage=0')
    return connect_list, {'intra': intra_conns, 'shortage': synchan_shortage}