Automating SPM Contrasts

Manually typing in contrasts in SPM is a grueling process that can have a wide array of unpleasant side effects, including diplopia, lumbago, carpal tunnel syndrome, psychosis, violent auditory and visual hallucinations, hives, and dry mouth. These symptoms are only compounded by the number of regressors in your model, and the number of subjects in your study.

Fortunately, there is a simply way to automate all of this - provided that each subject has the same number of runs, and that the regressors in each run are structured the same way. If they are, though, the following approach will work.

First, open up SPM and click on the TASKS button in the upper right corner of the Graphics window. The button is marked "TASKS" in capital letters, because they really, really want you to use this thing, and mitigate all of the damage and harm in your life caused by doing things manually. You then select the Stats menu, then Contrast Manager. The options from there are straightforward, similar to what you would do when opening up the Results section from the GUI and typing in contrasts manually.

When specifying the contrast vector, take note of how many runs there are per subject. This is because we want to take the average parameter estimate for each regressor we are considering; one can imagine a scenario where one of the regressors occurs in every run, but the other regressor only happens in a subset of runs, and this more or less puts them on equal footing. In addition, comparing the average parameter or contrast estimate across subjects is easier to interpret.

Once you have the settings to your satisfaction, save it out as a .mat file - for example, 'RunContrasts.mat'. This can then be loaded from the command line:

load('RunContrasts')

Which will put a structure called "jobs" in your workspace, which contains all of the code needed to run a first-level contrast. The only part of it we need to change when looping over subjects is the spmmat field, which can be done with code like the following:

subjList=[207 208]; %And so on, including however many subjects you want

for subj=subjList

    jobs{1}.stats{1}.con.spmmat =     {['/data/hammer/space4/MultiOutcome2/fmri/' num2str(subj) '/RESULTS/model_multiSess/SPM.mat']} %This could be modified so that the path is a variable reflecting where you put your SPM.mat file
    spm_jobman('run', jobs)

end

This is demonstrated in the following pair of videos; the first, showing the general setup, and the second showing the execution from the command line.





Contrasts in SPM (with Outtakes!)

We have come to the end of the preprocessing pipeline, and lurch across the finish line with a discussion of contrasts. Often researchers will calculate the difference in beta estimates between two conditions (in SPM, the beta_000?.img files), and also determine whether the difference is significant or not. At the single-subject level both the magnitude of the beta estimate and the variance of the estimate is calculated for each condition, and then t-tests can be performed on these beta estimates by weighting them. For example, the contrast of [1 -1] for Left vs. Right button presses will subtract the beta estimates for the Right button presses from the Left button presses, similar to a paired t-test. A t-statistic is then calculated at each voxel using the following formula:


Where gamma represents the contrast vector (in this example, [1 -1]) and B-hat represents the beta estimates for each condition. The degrees of freedom for a single-subject analysis is based on the number of time points; although, since nearby timepoints share a high degree of correlation, the actual degrees of freedom is pared down to compensate. With most standard processing streams, the variance associated with a beta estimate is discarded when carried to a higher-level analysis, although programs such as FSL's FLAME and AFNI's 3dMEMA take this variance into account when weighting group-level estimates.

Details about how to perform a simple t-contrast in SPM are shown in the following video. The first twenty seconds or so is an outtake where my microphone fell over; we sure like to have fun around here!