Skip to content

What is a connection weight made of?

The weight of a connection is a count of synapses from one cell to another. CAVE's synapse view has one row per synapse, and champalimaud.fetch counts the rows of each pair of cells (the outputs of a cell by its presynaptic id, its inputs by its postsynaptic id). If that is all a weight is, the rows of one cell should reproduce its stored weights exactly. synapses holds the rows of one LC16 cell, fetched once as the dataset example_synapses.

synapses = load_example_synapses()
cell = synapses["cell"][0]
synapses
shape: (1_273, 4)
cellidpre_pt_root_idpost_pt_root_id
i64i64i64i64
720575940606173630159305691720575940606173630720575940615645034
720575940606173630162802451720575940606173630720575940615645034
720575940606173630159304826720575940606173630720575940615645034
720575940606173630161891568720575940606173630720575940615645034
720575940606173630162803628720575940606173630720575940445991679
…………
720575940606173630190197806720575940616434260720575940606173630
720575940606173630190197390720575940616434260720575940606173630
720575940606173630190196942720575940622648703720575940606173630
720575940606173630190193625720575940622664522720575940606173630
720575940606173630190198656720575940609598475720575940606173630

Rows per pair

pairs counts the rows between each pair of cells.

pairs = (
    synapses.group_by("pre_pt_root_id", "post_pt_root_id")
    .agg(rows=pl.len())
    .sort("rows", descending=True)
)
pairs
shape: (692, 3)
pre_pt_root_idpost_pt_root_idrows
i64i64u32
72057594060617363072057594061336958625
72057594060617363072057594060660969624
72057594062749724472057594060617363017
72057594060617363072057594061564503416
72057594061969096872057594060617363014
………
7205759406109845167205759406061736301
7205759406113295017205759406061736301
7205759406240904937205759406061736301
7205759406237758437205759406061736301
7205759406376305657205759406061736301

Against the stored weights

stored is every connection in connections.parquet that starts or ends at the cell. The joined table has one row per pair, with the number of rows and the stored weight side by side.

stored = pl.concat(
    [
        load_connections_of([cell]),
        load_connections_of([cell], end="post"),
    ]
).unique()
compared = pairs.join(
    stored, on=["pre_pt_root_id", "post_pt_root_id"], how="full"
)
compared.select(
    pairs=pl.len(),
    only_in_rows=pl.col("weight").is_null().sum(),
    only_stored=pl.col("rows").is_null().sum(),
    equal=(pl.col("rows") == pl.col("weight")).sum(),
)
shape: (1, 4)
pairsonly_in_rowsonly_storedequal
u32u32u32u32
69200692

How the weight is spread

The number of pairs at each weight, and the synapses they hold. Most connections are one or two synapses, but the heavier ones hold a large share of all synapses.

pairs.group_by("rows").agg(pairs=pl.len()).with_columns(
    synapses=pl.col("rows") * pl.col("pairs")
).sort("rows").rename({"rows": "weight"})
shape: (16, 3)
weightpairssynapses
u32u32u32
1486486
2101202
336108
425100
51155
………
14228
16116
17117
24124
25125