# EEG
[TOC]
## Présentation / Avancement
### 1. Tâche de classification d'état de conscience : VS/MCS
> Pour rappel, nous avons accès à une base de 168 enregistrements (1 enregistrement par sujet, donc 168 sujets) en Resting State:
--- 82 sont en Vegetative State (VS)
--- 86 sont en Minimal Conscious State (MCS)
Les enregistrements sont effectués avec un montage hydrocel256 samplé à 250Hz et durent 5 minutes en moyenne.
Notre tâche principale est d'entraîner un modèle à classifier entre VS et MCS des nouveaux enregistrements de sujets jamais observés.
#### a) Préprocessing
> Nous chargeons et appliquons les préprocessing que vous nous avez fournis et obtenons en tout 28293 matrices de taille 256x201 :
--- 28293 "epochs"
--- 256 "channels" (hydrocel256)
--- 201 "samples" (250Hz)
Nous associons à chaque matrice la classe VS ou MCS.
Pour un enregistrement donné, notre modèle classifiera donc chaque matrice et associera à l'enregistrement la classe la plus prédite.
#### b) Train/val/test splits
> Afin de tester la capacité de généralisation de notre modèle à des sujets jamais observés, nous effectuons le split aléatoire par sujet suivant :
--- 75% des sujets appartiennent au training set (125 sujets, ~21k matrices)
--- 12.5% des sujets au validation set (21 sujets, ~3.5k matrices) que nous utilisons pour décider quand arrêter l'entrainement de notre modèle
--- 12.5% des sujets au testing set (22 sujets, ~3.5k matrices) que nous utilisons pour l'évaluation finale de notre modèle.
#### c) Résultats
> Nous n'obtenons pas de meilleurs résultats qu'un classifieur aléatoire.
> Nous avons essayé plusieurs modèles :
--- support vector machine, linéaire ou à noyau, avec ou sans réduction des dimensions (PCA), sur les matrices aplaties (vecteur 256*201, concaténation des "channels")
--- réseau de neurones
> Nous avons aussi essayé différents préprocessings comme :
--- sélectionner uniquement les enregistrements ayants le moins de "bad" epochs et de "bad" channels.
--- réutiliser les préprocessings des derniers résultats que nous vous avions présentés (slides) consistants à réduire le nombre de channels en approximant un montage 10-20 (Luu et al. 2005) et à utiliser une fréquence d'échantillonnage de 100Hz au lieu de 250Hz.
### 2. Tâche de classification d'état de conscience: VS/MCS au sein d'un même sujet
> Afin de comprendre le problème, nous sommes passés à une tâche de classification au sein d'un même sujet ; au lieu de splitter par sujet, nous splittons au sein de chaque sujet :
--- les 50 premiers % d'un enregistrement appartiennent au training set
--- les 25% suivants au validation set
--- les 25 derniers % au testing set
> Cette fois-ci, nous obtenons de bons résultats (~82% de bonne classification, l'aléatoire étant à 50%).
### 3. Tâche de classification de sujets (167 sujets)
> Toujours afin de comprendre le problème, nous avons aussi réutilisé notre code de classification de sujets (slides).
Ce code fonctionnait bien, même en généralisation sur des sujets jamais observés sur une base de données plus petite que vous nous avez confié précédemment. Comme nous avons uniquement 1 enregistrement par sujet, ici nous pouvons uniquement tester la généralisation au sein des sujets en splittant comme précédemment :
--- les 50 premiers % d'un enregistrement appartiennent au training set
--- les 25% suivants au validation set
--- les 25 derniers % au testing set
>Nous obtenons d'encore meilleurs résultats (~88% de bonne classification, l'aléatoire étant à 0.6%).
### 4. Conclusion
> Nous n'arrivons pas à classifier VS/MCS en généralisation d'un sujet à un autre.
En d'autres termes, nous n'arrivons pas à capturer des signatures "VS" ou "MCS"
> Par contre, nous arrivons à classifier VS/MCS en généralisation au sein d'un même sujet.
En particulier, nous arrivons à identifier à quel sujet appartient des parties d'enregistrement jamais observé parmi 167 sujets.
Nous pensons que ces deux succès sont dûs au fait que nous arrivons à capturer les signatures de chaque enregistrement.
Nous arriverions dans ce cas à classifier VS/MCS en utilisant ces signatures propres à chaque enregistrement et non pas en utilisant des signatures "VS" ou "MCS".
### 5. Bilan / Next steps
> Pour l'instant, vous nous avez fourni un code permettant de charger et de prétraiter vos données, mais nous n'avons aucun moyen de vérifier si ce code fonctionne correctement sur nos machines. Comme nous n'avons malheureusement eu aucun retour malgré nos relances, nous avons fait tout ce que nous pouvions faire seuls, mais nous ne pouvons plus progresser davantage sur ce projet en l'état.
> Il est désormais indispensable que vous nous aidiez à vérifier que votre code fonctionne bien sur nos machines, par exemple en nous donnant accès à votre code permettant de reproduire vos résultats de classification.
> On hâte de pouvoir continuer cette collaboration ! :)
> Bien cordialement,
Remi, Remy et Matthieu
## Tâche
Classifier pour une personne donnée l'etat de conscience dans lequel elle se trouve.
## Datasets
### PICNIC
petit dataset, privé, Salpêtrière
256 channels
### TUH
petit dataset, public, université allemande.
21 channels - 3 = 18 channels
### ICM
gros dataset, privé, Salpêtrière
256 channels
`next_icm/rs/markers.py`
markers code might be used to extract "consciousness" features
`next_icm/rs/preprocessing.py`
preprocessing code
sur Picnic et ICM, on élimine des channels pour retomber sur 18 channels comme TUH
## Terminologie
- **Sample**: Enregistrement sur e.g. 256 channels, chacun enregistrés à e.g. 250Hz (une valeur toutes les 4 ms).
-> matrice de 256 x (250 x T_max)
- **Frame/Epoch**: Fenêtre de découpage du sample sur un certain intervalle de temps. On cherche à ce que la largeur de cette frame soit suffisante pour capturer les signal recherché (en l'occurence, l'état de conscience).
## Commandes Slurm
Lister les nodes
```bash
sinfo
```
Lister les jobs queued
```bash
squeue
```
Réserver un node pour 300 minutes
```bash
srun -N1 --gpus-per-node=1 --mem=32GB --cpus-per-task 4 -t 300 --pty bash
```
Lancer un job
```bash
sbatch --mem=56GB \
--cpus-per-task=10 \
--gres=gpu:1 \
--time=5400 \
--partition="electronic" \
--comment="genexplain" \
--output="/data/cadene/slurm/%j.out" \
--error="/data/cadene/slurm/%j.err" \
--wrap="python -m christophe.bouder -o cbd"
```
## Env
```bash
conda activate torchray
```
## Commandes test
```
python -m bootstrap.run \
-o eeg/options/tuh.yaml \
--exp.dir logs/tuh/2022_01_03_test
# not working
python -m bootstrap.run \
-o eeg/options/picnic_nperson,18.yaml \
--exp.dir logs/picnic/2022_01_03_nperson,18_test
python -m bootstrap.run \
-o eeg/options/picnic_nperson,35.yaml \
--exp.dir logs/picnic/2022_01_03_nperson,35_test
python -m bootstrap.run \
-o eeg/options/icm_256.yaml \
--exp.dir logs/icm/2022_01_03_montage,256_test
```
## Options
- dataset:
- split_ids_type: `inter` si task=`clf_state` (une seule personne ou non si on classifie l'état plutôt que l'identité)
- preprocess:
- montage: montage des electrodes
- notches: fréquences supprimées car appartenant à certains instruments
- t_cut: largeur de la frame
## TODO ICM
- Exploratoire : Regarder les donnees, ploter les channels EEG, detecter les periodes.
https://mne.tools/stable/generated/mne.Epochs.html
`eeg/datasets/icm.py l.290`
```python
fig = epochs.plot(
show=False,
block=False,
n_epochs=len(epochs),
n_channels=256
)
fig.savefig('logs/test.png')
```
-
- plotter sur plusieurs epochs
- Explorer un channel pour plusieurs patient
- Indicateurs statistiques (mean, std) global / par patient
- Augmentation de chaque frame avec des features statistiques globales de l’enregistrement ou locales (precedente frame et frame suivante)
- Finetuner depuis pre-entrainement classif de personne
- Triplet loss de distance entre frame
- Concatenation de plusieurs frames
- Baseline statistiques
16 descirpteurs par fame et 32 pour chaque echantillon (moyenne et variance)