Note
Go to the end to download the full example code or to run this example in your browser via Binder
Functional connectivity predicts age group#
This example compares different kinds of functional connectivity between regions of interest : correlation, partial correlation, and tangent space embedding.
The resulting connectivity coefficients can be used to discriminate children from adults. In general, the tangent space embedding outperforms the standard correlations: see Dadi et al 2019 for a careful study.
Note
If you are using Nilearn with a version older than 0.9.0
, then you should either upgrade your version or import maskers from the input_data
module instead of the maskers
module.
That is, you should manually replace in the following example all occurrences of:
from nilearn.maskers import NiftiMasker
with:
from nilearn.input_data import NiftiMasker
Load brain development fMRI dataset and MSDL atlas#
We study only 60 subjects from the dataset, to save computation time.
from nilearn import datasets
development_dataset = datasets.fetch_development_fmri(n_subjects=60)
Downloading data from https://osf.io/download/5c8ff3eb2286e80019c3c198/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3ed2286e80017c41b56/ ...
Downloaded 4497408 of 5919127 bytes (76.0%, 0.3s remaining) ...done. (4 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3ee2286e80016c3c379/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3ee4712b400183b70c3/ ...
Downloaded 4349952 of 5642114 bytes (77.1%, 0.3s remaining) ...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3efa743a9001660a0d5/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3f14712b4001a3b560e/ ...
Downloaded 3981312 of 6081959 bytes (65.5%, 0.5s remaining) ...done. (4 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3f1a743a90017608164/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3f12286e80016c3c37e/ ...
Downloaded 5373952 of 5880763 bytes (91.4%, 0.1s remaining) ...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3f34712b4001a3b5612/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3f7a743a90019606cdf/ ...
Downloaded 4186112 of 6432694 bytes (65.1%, 0.5s remaining) ...done. (4 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3f6a743a90017608171/ ...
...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3f64712b400183b70d8/ ...
Downloaded 4579328 of 5606383 bytes (81.7%, 0.2s remaining) ...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3f72286e80019c3c1af/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3f92286e80018c3e463/ ...
Downloaded 4972544 of 6274191 bytes (79.3%, 0.3s remaining) ...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5cb47057f2be3c0019030a1f/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5cb46e63f2be3c0017056ba9/ ...
Downloaded 4022272 of 6123172 bytes (65.7%, 0.5s remaining) ...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5cb4704af2be3c001705703b/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5cb46e7a353c58001a9b3324/ ...
Downloaded 4734976 of 6203305 bytes (76.3%, 0.3s remaining) ...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3952286e80016c3c2e7/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3954712b400193b5b79/ ...
Downloaded 4227072 of 6253721 bytes (67.6%, 0.5s remaining) ...done. (4 seconds, 0 min)
Downloading data from https://osf.io/download/5cb47016a3bc970018f1fc88/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5cb46e6ba3bc970019f07152/ ...
Downloaded 4653056 of 6168810 bytes (75.4%, 0.3s remaining) ...done. (4 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff395a743a900176080af/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3964712b400193b5b7d/ ...
Downloaded 3776512 of 6287468 bytes (60.1%, 0.7s remaining) ...done. (4 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff399a743a9001660a031/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3982286e80017c41a29/ ...
Downloaded 4218880 of 6146235 bytes (68.6%, 0.5s remaining) ...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff39aa743a90018606e21/ ...
...done. (1 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff39aa743a900176080ba/ ...
Downloaded 4472832 of 6358784 bytes (70.3%, 0.4s remaining) ...done. (4 seconds, 0 min)
Downloading data from https://osf.io/download/5cb470153992690018133d3b/ ...
...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5cb46e793992690017108eb9/ ...
Downloaded 4259840 of 6199206 bytes (68.7%, 0.5s remaining) ...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5cb47038353c5800199ac9a2/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5cb46e85a3bc97001aeff750/ ...
Downloaded 4341760 of 6249029 bytes (69.5%, 0.4s remaining) ...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5cb4701c3992690018133d49/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5cb46e1c3992690018133a9e/ ...
Downloaded 4481024 of 5741735 bytes (78.0%, 0.3s remaining) ...done. (4 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff39aa743a900176080bf/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff39d4712b400193b5b89/ ...
Downloaded 4481024 of 5950135 bytes (75.3%, 0.3s remaining) ...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5cb4703039926900160f6b3e/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5cb46e4d353c58001b9cb325/ ...
Downloaded 4292608 of 5967515 bytes (71.9%, 0.4s remaining) ...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5cb4700af2be3c0017056f69/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5cb46e0cf2be3c001801f757/ ...
Downloaded 4218880 of 5527830 bytes (76.3%, 0.3s remaining) ...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5cb4702b39926900171090e4/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5cb46e35f2be3c00190305ff/ ...
Downloaded 4505600 of 5894024 bytes (76.4%, 0.3s remaining) ...done. (4 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff39ca743a90019606c50/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3a2a743a9001660a048/ ...
Downloaded 5021696 of 6131100 bytes (81.9%, 0.2s remaining) ...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5cb4701ff2be3c0017056fad/ ...
...done. (1 seconds, 0 min)
Downloading data from https://osf.io/download/5cb46e0339926900160f6930/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3a12286e80017c41a48/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3a12286e80016c3c2fc/ ...
Downloaded 5652480 of 6235792 bytes (90.6%, 0.1s remaining) ...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff39fa743a90018606e2f/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3a34712b4001a3b55a3/ ...
...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5cb4703439926900160f6b43/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5cb46e40f2be3c001801f77f/ ...
Downloaded 4136960 of 5926863 bytes (69.8%, 0.4s remaining) ...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3a34712b400193b5b92/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3a84712b400183b7048/ ...
Downloaded 4055040 of 5552738 bytes (73.0%, 0.4s remaining) ...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5cb47020f2be3c0019030968/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5cb46e6f353c58001a9b3311/ ...
Downloaded 3661824 of 6178036 bytes (59.3%, 0.7s remaining) ...done. (4 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3a72286e80017c41a54/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5c8ff3a7a743a90018606e42/ ...
Downloaded 4366336 of 5978758 bytes (73.0%, 0.4s remaining) ...done. (3 seconds, 0 min)
Downloading data from https://osf.io/download/5cb4702639926900190faf1d/ ...
...done. (2 seconds, 0 min)
Downloading data from https://osf.io/download/5cb46e3f353c5800199ac787/ ...
Downloaded 4087808 of 5920556 bytes (69.0%, 0.4s remaining) ...done. (3 seconds, 0 min)
We use probabilistic regions of interest (ROIs) from the MSDL atlas.
from nilearn.maskers import NiftiMapsMasker
msdl_data = datasets.fetch_atlas_msdl()
msdl_coords = msdl_data.region_coords
masker = NiftiMapsMasker(
msdl_data.maps,
resampling_target="data",
t_r=2,
detrend=True,
low_pass=0.1,
high_pass=0.01,
memory="nilearn_cache",
memory_level=1,
standardize="zscore_sample",
standardize_confounds="zscore_sample",
).fit()
masked_data = [
masker.transform(func, confounds)
for (func, confounds) in zip(
development_dataset.func, development_dataset.confounds
)
]
What kind of connectivity is most powerful for classification?#
we will use connectivity matrices as features to distinguish children from adults. We use cross-validation and measure classification accuracy to compare the different kinds of connectivity matrices.
# prepare the classification pipeline
from sklearn.dummy import DummyClassifier
from sklearn.model_selection import GridSearchCV
from sklearn.pipeline import Pipeline
from sklearn.svm import LinearSVC
from nilearn.connectome import ConnectivityMeasure
kinds = ["correlation", "partial correlation", "tangent"]
pipe = Pipeline(
[
(
"connectivity",
ConnectivityMeasure(
vectorize=True,
standardize="zscore_sample",
),
),
(
"classifier",
GridSearchCV(LinearSVC(dual=True), {"C": [0.1, 1.0, 10.0]}, cv=5),
),
]
)
param_grid = [
{"classifier": [DummyClassifier(strategy="most_frequent")]},
{"connectivity__kind": kinds},
]
We use random splits of the subjects into training/testing sets. StratifiedShuffleSplit allows preserving the proportion of children in the test set.
from sklearn.model_selection import GridSearchCV, StratifiedShuffleSplit
from sklearn.preprocessing import LabelEncoder
groups = [pheno["Child_Adult"] for pheno in development_dataset.phenotypic]
classes = LabelEncoder().fit_transform(groups)
cv = StratifiedShuffleSplit(n_splits=30, random_state=0, test_size=10)
gs = GridSearchCV(
pipe,
param_grid,
scoring="accuracy",
cv=cv,
verbose=1,
refit=False,
n_jobs=8,
)
gs.fit(masked_data, classes)
mean_scores = gs.cv_results_["mean_test_score"]
scores_std = gs.cv_results_["std_test_score"]
Fitting 30 folds for each of 4 candidates, totalling 120 fits
display the results
from matplotlib import pyplot as plt
plt.figure(figsize=(6, 4))
positions = [0.1, 0.2, 0.3, 0.4]
plt.barh(positions, mean_scores, align="center", height=0.05, xerr=scores_std)
yticks = ["dummy"] + list(gs.cv_results_["param_connectivity__kind"].data[1:])
yticks = [t.replace(" ", "\n") for t in yticks]
plt.yticks(positions, yticks)
plt.xlabel("Classification accuracy")
plt.gca().grid(True)
plt.gca().set_axisbelow(True)
plt.tight_layout()
This is a small example to showcase nilearn features. In practice such comparisons need to be performed on much larger cohorts and several datasets. Dadi et al 2019 Showed that across many cohorts and clinical questions, the tangent kind should be preferred.
plt.show()
Total running time of the script: (3 minutes 57.897 seconds)
Estimated memory usage: 1187 MB