Second-Level Analysis using gen_group_command.py
Second-level analysis takes the results from the first-level analysis (individual subjects) and combines them across participants. This allows us to make inferences about the population as a whole, rather than just describing one person’s brain activity.
In some studies, researchers might compare different groups (e.g., males vs. females, patients vs. controls). However, in our case all subjects in Demodat2 performed the same task, and we did not divide them into subgroups. Therefore, we will use a one-sample test to examine whether the group, as a whole, shows consistent brain activation.
The Full Script
Below you can find the full group analysis preprocessing example script.
Understanding the Script
Overview
AFNI provides an example script (s.nimh_group_level_02_mema_bisided.tcsh) that accepts output from afniproc.py, and puts that output through a series of steps to run group analysis. The general workflow is as follows:
Set up paths and parameters
Voxelwise modeling via gen_group_command.py
Make a group mask using AFNI's 3dmask_tool
Calculate the average smoothness
Clusterize
Here we provide a version of this script that is written in bash and intended to be launched as a batch script on Oscar.
Step 1: Set up paths and parameters
Step 2: Voxelwise modeling via gen_group_command.py
Similar to how afniproc.py generates a processing script per subject, AFNI's gen_group_command.py generates group analyses scripts. We will be using this meta-script to write a group analysis command that uses 3dMEMA.
AFNI's 3dMEMA performs a "mixed effects meta analysis", which, based on your experimental design, could take the form of t-tests, ANOVAs, ANCOVAs, and more. 3dMEMA differs from 3dttest++ in that it weights each subject's beta coefficient according to the respective t-statistic. This means that voxels with higher t-values will be weighted more heavily in the group analysis. To achieve this, you must provide the t-statistic sub-brick as well as the beta coefficient (both output from 3dREMLfit).
gen_group_command.py options
-command 3dMEMAspecifies that we will be using 3dMEMA as our statistical test-write_scriptnames the group analysis script-prefixspecifies what name/prefix will be included in the output files-dsetslists the data to be used in the group analysis. In this case, we are using the statistical files generated by 3dREMLfit for each subject of demodat2 (this is one of the outputs of afniproc.py)-set_labelsare the labels which correspond to the two tasks we ran (chx and keypress)-subs_betaslists the sub-bricks of the REML statistical files which correspond to the beta coefficients for each task. Beta files for each task should be listed in the same order as they were in -set_labels (chx then keypress)-subs_tstatslists the t-statistic sub-bricks for each respective task-options -missing_data 0The-missing_dataflag controls what 3dMEMA should do when a subject is missing data in a voxel. By passing it0, we are ensuring that each voxel with missing data (NaN, 0) in it will NOT be included in group level statistical analysis. A voxel will still be included on the group level as long as at least 2 subjects have valid data. This is important because it prevents distortion of the group-level variance estimates and and produces more reliable mixed-effects group statistics
gen_group_command.py generates the group analysis script in tcsh, but does not execute it. Following file creation, it is launched via the line tcsh -ef "${outdir}/${script_mema}"
Step 3: Make a group mask using AFNI's 3dmask_tool
Next, AFNI's 3dmask_tool is used to collect all subject-level masks created during single-subject processing, and combine them into one group level intersection mask. This mask will be used in subsequent steps.
Step 4: Calculate the average smoothness
Along with the mask, group‐level cluster correction in AFNI (via 3dClustSim) requires estimates of spatial smoothness. These estimates come from each subject’s residuals and must be averaged across subjects.
AFNI's recommended smoothness metric is the REML-based ACF (Autocorrelation Function), which models spatial noise with 3 parameters. The -acf method is preferred because it will give more accurate false positive rate (FPR) control.
Understanding the code, line by line:
blur_est_lines=$(grep "err_reml ACF" ${path_proc}/sub*/sub*results/blur_est* | awk -F':' '{print $2}' | awk '{print $1, $2, $3}')
grep "err_reml ACF"Finds the REML ACF line inside each subject’s
blur_estfile.Each subject’s
blur_estfile contains several lines; we want the one that includes REML ACF measurements:This is the 4-parameter ACF:
3 ACF parameters follower by a FWHM-like combined smoothness value. We keep only the first three numbers.
awk -F':' '{print $2}'Removes the filename prefix and keeps just:
awk '{print $1, $2, $3}'Takes only the first 3 numbers, which are all that's needed by 3dClustSim.
The resulting variable
blur_est_linesis:
A check is included at the end ("
if [[ -z "$blur_est_lines" ]]; then...") to ensure that the values were properly parsed from theblur_est*file.
read a b c <<< "$(echo "$blur_est_lines" | awk '{a+=$1; b+=$2; c+=$3; n+=1} END {print a/n, b/n, c/n}')"
From the
blur_est_linesarray, assign the columns to the variablesa,b, andc.Creates a group average for
a,b, andcby adding the values of each column together and dividing that by the total number of subjects.
blur_est=("$a" "$b" "$c"")
A new variable is created called
blur_est, which contains the mean of each ACF parameter across subjects. This will be used in 3dClustSim.
Step 5: Cluster Simulations using 3dClustSim
3dClustSim is AFNI’s tool for estimating family-wise error (FWE)–corrected cluster-size thresholds based on the spatial smoothness of your data. This is done using Monte Carlo simulations, to determine how large a cluster must be to be unlikely to appear by chance, given:
your choice of sidedness
a group level mask
your spatial smoothness (ACF parameters)
3dClustSim outputs a full table of cluster-size thresholds across a range of voxelwise p-values and FWE levels. Because we used -both, 3dClustSim produces two output tables:
Nearest-neighbor face-only clustering (NN=1)
Nearest-neighbor face+edge+corner (NN=2)
Later steps extract cluster-size thresholds from the desired output table.
Step 5: Compute voxelwise statistical thresholds for both tasks
This section takes the 3dClustSim table you generated earlier and uses it to compute two things:
The minimum cluster size needed to survive FWE correction.
The voxelwise statistical threshold (e.g., Z, t, or F threshold) that corresponds to your chosen voxelwise p-value.
This information will then be passed to 3dClusterize.
Step 6: Make thresholded cluster maps
This final section produces thresholded activation maps, using many of the variables and outputs defined in previous code. Notably, it uses 1) the voxelwise threshold, 2) the cluster-size threshold, 3) test sidedness (e.g., bisided), and 4) the neighborhood definition (NN1, NN2, NN3).
For more information, please refer to AFNI's documentation on 3dClusterize.
View the Output
First, let's view the output of 3dMEMA. In a terminal, navigate to the output directory ($bids_dir/derivatives/afni/GROUP_ANALYSIS) and open afni by typing afni on the command line. Using the afni GUI, select MNI152_2009_template.nii.gz as the Underlay, and mema_results.nii.gz as the Overlay.
Expand the window by clicking the Define Overlay --> button , and set the Olay to the beta coefficient map for the checks task (chx:b). Se the threshold to chx:t. Finally, select a p-value (In our example, we chose 0.01). You can now scroll through the viewer and observe areas of visual activation.
The same thing can be done for the keypress task by selecting the Olay as keypress:b and the threshold as keypress:t.
Remember: At the stage in the pipeline, no group mask has been applied, which is why you see voxels outside the brain.

The final output of this pipeline is the thresholded effect estimate (EE) map (clust_bisided_EE_chx.nii.gz). An effect estimate is the scaled beta coefficient (β) for a regressor, in units of percent signal change. The EE map is masked by significant clusters, thresholded at the chosen p-value, and corrected for whole-brain cluster-level FWE. In our case, it is in MNI space as well. Importantly, these maps only contain significant clusters, and all other voxels are set to 0. There were no significant clusters found for the keypress task- likely due to our low N. This is why you will see a report for the keypress task in the final output folder, but no EE map or cluster map. However, active clusters were output for the checks task!
You can view the effect estimate map for the checks task by changing the overlay in the AFNI GUI to clust_bisided_EE_chx.nii.gz.

To summarize, the voxel values in these effect-estimate maps are group-level % signal-change values derived from the subject-level beta coefficients. Unlike the output from 3dMEMA that we just looked at above, these maps are masked to only include significant clusters. Values can be extracted from these final output files (clust_bisided_EE_chx.nii.gz, clust_bisided_map_chx.nii.gz, and clust_bisided_report_chx.txt) to be reported in your final analysis.
Last updated
Was this helpful?