Source Reconstruction and Population Codes

This tutorial explains the concepts behind pyAVS’s source reconstruction pipeline and where to find the runnable code for each step. For copy-pasteable code, see Source Reconstruction Examples – this page focuses on why each step exists and how the pieces fit together.

Why Beamforming?

pyAVS’s source reconstruction is built around LCMV beamforming (Linearly Constrained Minimum Variance): a spatial filter, computed per subject/session from a forward model and a data/noise covariance estimate, that projects sensor-space MEG data onto estimated cortical source activity. This is the same family of method used for the source-projected fixation ERFs described in Example Analyses and in the Methods section (Source Reconstruction).

The pipeline has three stages:

  1. Forward modelingpyavs.create_bem_model(), pyavs.create_source_space(), pyavs.setup_coregistration(), pyavs.load_forward_model() combine a subject’s structural MRI (FreeSurfer reconstruction) and MEG sensor geometry into a forward solution: how activity at each cortical location would project onto each sensor.

  2. Filter computationpyavs.compute_beamformer_filters() (or, for filters shared across a session, compute_per_session_lcmv_filters()) inverts that relationship given a data covariance estimate, producing a spatial filter per source location.

  3. Application and summarization – the filters are applied to epoched data (pyavs.apply_source_reconstruction() or apply_beamformer()) to get per-epoch source-space data, which can then be summarized within regions of interest (pyavs.extract_roi_data()) and averaged into condition-level population codes (pyavs.compute_population_codes()).

Why Per-Session Filters?

Because AVS sessions are recorded on different days (median 2 days apart, up to 93 days – see Participants), head position relative to the MEG sensors drifts between sessions despite the individualized head-stabilizing casts. Computing beamformer filters independently per session, but from a shared cross-session data covariance estimate (compute_cross_session_data_covariance()), keeps the source estimates comparable across sessions without needing millimeter-perfect repositioning. See Cross-Session Beamformer Filters for the standalone script that computes this, and Source Reconstruction Examples for how the filters are then applied within the full population-code pipeline.

From Source Data to Population Codes

Raw source-reconstructed data has shape (n_epochs, n_sources, n_times) – one value per cortical source location, per timepoint, per epoch. Two further steps make this usable for encoding/RSA-style analyses:

Results are saved via pyavs.save_population_codes_h5() in a standardized HDF5 format, and can be rediscovered later with pyavs.find_population_codes_files() and pyavs.list_available_parameter_sets().

Next Steps