Hi all. I am working on an approach to automatically process resting state EEG recordings from many participants before extracting some features. Processing includes:
filtering
epoching
blink artifact removal (I use Fp1 as proxy to eog channel)
bad epoch rejection
Considering raw is the continous EEG recording for a participant, I have implemented the following pipeline:
This will include eog in the returned reject dictionary – which might not be what you want, as it will lead to the removal of epochs with blinks. You may wish to consider passing ch_types='eeg' to only retrieve a rejection threshold for EEG.
Note that reject is simply ignored if you pass epochs to ICA.fit(). This is a little bit hidden in the documentation (and a reminder for me that we should add a clear warning):
If you want to fit ICA on epochs with a peak-to-peak rejection threshold applied, you must drop the bad epochs before ICA, either by calling Epochs.drop_bad() or by passing reject to Epochs() on instantiation.
Yes, this is a good idea. In fact, it appears that using autoreject “local” before and after ICA is in fact a good choice – we were seeing some issues with autoreject “global” before ICA in EEG layouts with some electrodes placed close to the eyes, like Fp1/Fp2. The respective tutorial has been updated very recently by @mainakjas:
I think it has not yet been deployed to the autoreject documentation website, therefore I’m linking to the file on GitHub.
That’s what we do in the MNE-BIDS-Pipeline before ICA. However, the problem with fixed thresholds is that … they’re fixed (surprise!), and the same thresholds might now work across all participants in your study. On the other hand, autoreject “global” led to problems in some of our datasets (see my comments above), and running auroreject “local” twice (before and after ICA) can be quite time-consuming. It’s a tradeoff, really.
Yes, autoreject after ICA is the correct order. You can also apply it before, and use the bad epochs detected to improve ICA decomposition. Local autoreject before ICA seems to work better than global autoreject. If you’re lazy, you could also just use a high threshold like 500 uV pre-ICA. I haven’t investigated in detail the impact of these different choices, so make sure to inspect your data.
See 1.
I’m not exactly sure what kind of features you’re talking about. If you intend to do some machine learning, I would normalize the features, yes.
Please, feel free to comment anything else you deem valuable. The tutorial you both pointed me to was really helpful.
I have some concerns regarding this procedure:
Is it good practice to use AutoReject after applying ICA?
Should I use a fixed threshold (like 100 uV) instead of applying AutoReject?
After all the processing, should I normalize my epochs prior to feature extraction?
Finally, regarding my third question here, let me clarify things: I want to extract features (like sample entropy, PSD, fractal dimension, etc.) from the clean epochs. I am aware, after extracting the features, I need to scale them before passing them to the learning algorithm. My question is, do I also need to standarize the EEG epochs before extracting the features?