help > RE: Global signal calculation
Sep 28, 2016  10:09 AM | Pravesh Parekh - National Institute of Mental Health and Neurosciences
RE: Global signal calculation
Dear Dr. Alfonso,

Just to make sure that everything was being done correctly, I did the following:

Calculated REX time series using:
HS034_rex_signal = rex('waursfMRI.nii', 'C:\Program Files\MATLAB\R2015a\toolbox\conn\utils\surf\mask.volume.brainmask.nii', 'summary_measure', 'mean', 'level', 'rois', 'scaling', 'roi');
HS034_rex_signal_psc = ((HS034_rex_signal-mean(HS034_rex_signal))/mean(HS034_rex_signal))*100;

Calculated GS using my original function:
HS034_globalsignal_psc = calculate_global_signal_psc('waursfMRI.nii');

and calculated GS using the modification that you had suggested:
HS034_globalsignal_psc_mod = calculate_global_signal_psc('waursfMRI.nii');


The differences are still there. I am attaching a MATLAB variable with the four outputs (and also the original REX file) for your reference.

The calculate_global_signal_psc function is replicated here for your reference (its the same code as before, with the modification you suggested):

function [global_signal_psc] = calculate_global_signal_psc(image_files, mask_file)

if nargin == 1
mask_file = which('surf/mask.volume.brainmask.nii');
end

image_files_read = spm_vol(image_files);
num_volumes = length(image_files_read);

mask_file_read = spm_vol(mask_file);
mask_file_volume = spm_read_vols(mask_file_read);

global_signal = zeros(num_volumes,1);

for vol_idx = 1:num_volumes
image_file_volume = spm_read_vols(image_files_read(vol_idx));
masked_volume = image_file_volume.*mask_file_volume;
validvoxels = image_file_volume~=0;
global_signal(vol_idx,1) = mean(masked_volume(validvoxels));
% global_signal(vol_idx,1) = mean(mean(mean(masked_volume)));
end

mean_global_signal = mean(global_signal);

% Calculate percent signal change with reference to the mean global signal
global_signal_psc = ((global_signal-mean_global_signal)/mean_global_signal)*100;
end


Yours sincerely
Pravesh

Originally posted by Pravesh Parekh:
Dear Dr. Alfonso,

Based on your suggestions, I cross-checked the following:

- I am working in the correct subject folder
- I have the correct REX file
- The params.sources field reads '\*\waursfMRI.nii'
- The params.rois filed reads '*\conn\utils\surf\mask.volume.brainmask.nii'
- The input for my function for global signal calculation is indeed the waursfMRI.nii file
- I am using the default option and that time series is being extracted from the normalized, non-smoothened files
- The params.output_rex reads 'REX_Subject001_Session001_ROI4.mat' while the fourth ROI in my Conn GUI corresponds to mask_volume_brainmask

I also tried implementing the modification that you had suggested, but I still see the same minor difference. Any other suggestions on what might be happening?



Yours sincerely
Pravesh
Originally posted by Alfonso Nieto-Castanon:
Dear Pravesh,

I probably should have first checked another potential often-missed factor: could you please double-check that the variable image_files in your code is pointing to the same functional volumes that are being used by CONN to extract BOLD data from? In particular if you are using all of the default settings, then the BOLD signal data within the ROI will be extracted from unsmoothed volumes (i.e. wau* files) instead of the smoothed volumes (i.e. swau* files), which may also explain some minor discrepancies.

Best
Alfonso 

Originally posted by Alfonso Nieto-Castanon:
Dear Pravesh,

Yes, the code looks perfectly fine, the only subtlety that I can think of that may be causing the slight discrepancies would be the following. CONN uses REX to extract the BOLD signal at the ROI location, which internally checks whether any ROI voxels do not contain valid BOLD data and disregards any such voxel. In particular, valid BOLD data is determined by: a) if your BOLD timeseries has a NaN representation (i.e spm_type(...,'nanrep') returns a 1) then NaN's indicate invalid/missing BOLD data; or b) otherwise exact 0's represent invalid/missing BOLD data. If, for example, your acquisition does not cover the entire brainmask volume, then, after realignment and normalization, some portion of your BOLD volumes will contain NaN's or 0's to indicate that they originated from regions beyond your actual BOLD acquisition volume. REX may be disregarding such regions when computing the average BOLD signal within the brainmask volume (and these regions may vary from one scan to the next, due to differences in the estimated subject movement parameters and associated realignment correction). One possible way to check whether this is what is causing your observed discrepancies would be to change the line in your code that read:

global_signal(vol_idx,1) = mean(mean(mean(masked_volume)));

to something like:

validvoxels = image_file_volume~=0;
global_signal(vol_idx,1) = mean(masked_volume(validvoxels));

Let me know if this seems to explain the differences
Best
Alfonso
Originally posted by Pravesh Parekh:
Dear Dr. Alfonso/Conn Users,

Greetings!

Thank you for the many detailed discussions on global signal on other threads. Based on that, I wanted to confirm the method by which Conn calculates the global signal. I have written a brief method for the same below, wherein I am masking my functional data with 'mask.volume.brainmask.nii' file (Conn default), calculating the mean across all the voxels that are included in the mask for each functional volume, and at the end calculating PSC with respect to the mean global signal. Would this be the way Conn would calculate global signal (when including an explicit ROI for brainmask) or am I missing something? I have plotted both of them (params.ROIdata in the appropriate REX file and the global signal estimated from the lines below). They are mostly identical save for very slight differences at a few points. I know that these differences are not much and might be insignificant, still how do we explain the slight differences?

image_files_read = spm_vol(image_files);
num_volumes = length(image_files_read);

mask_file_read = spm_vol('mask.volume.brainmask.nii');
mask_file_volume = spm_read_vols(mask_file_read);

global_signal = zeros(num_volumes,1);

for vol_idx = 1:num_volumes
image_file_volume = spm_read_vols(image_files_read(vol_idx));
masked_volume = image_file_volume.*mask_file_volume;
global_signal(vol_idx,1) = mean(mean(mean(masked_volume)));
end

mean_global_signal = mean(global_signal);

% Calculate percent signal change with reference to the mean global signal
global_signal_psc = ((global_signal-mean_global_signal)/mean_global_signal)*100;


Thank you so much for your time and continued help and support!


Warm Regards
Pravesh
Attachment: HS034_signals.mat

Threaded View

TitleAuthorDate
Pravesh Parekh Sep 22, 2016
Sascha Froelich Oct 5, 2016
Pravesh Parekh Oct 5, 2016
Alfonso Nieto-Castanon Sep 28, 2016
Alfonso Nieto-Castanon Sep 28, 2016
Pravesh Parekh Sep 28, 2016
RE: Global signal calculation
Pravesh Parekh Sep 28, 2016
Alfonso Nieto-Castanon Sep 28, 2016
Pravesh Parekh Sep 28, 2016
Sascha Froelich Sep 26, 2016
Pravesh Parekh Sep 26, 2016
Sascha Froelich Sep 23, 2016
Pravesh Parekh Sep 23, 2016
Sascha Froelich Sep 23, 2016
Pravesh Parekh Sep 26, 2016
Sascha Froelich Sep 26, 2016
Pravesh Parekh Sep 26, 2016