User Tools

Site Tools


Sidebar

Home

EEGLAB Hackathon
Scripts
Main Website
Contact

bastien.b1@gmail.com

eeglabsessh1b

This is an old revision of the document!


Be patient :) This page will go live on Wed, 5th at 10am.

Until then, check the overview page where you will find all the info about the hackathon.
You can also download the necessary files here.

Getting cosy with EEGLAB: Batch Crews

1. Basic programming tips & loops

As we said earlier, the ultimate goal is to be able to automatise the processing pipeline. Imagine having to go through 20 participants manually and waiting for each steps to be processed to carry on, in the case of long steps like ICA, it would probably take you days to just pre-process your data. We will therefore want to write our own batch scripts to automatise some of the processes.

EEG/ERPLab commands

  • All functions corresponding to EEGLAB menus are listed here and all EEGLAB functions even those not currently attached to a GUI menu can be found here.
  • Every menu window should have the name of the function it will call, which makes it easy to know which function to call when scripting.
  • Just like with any function MATLAB will have a help file stored which gives helpful details about each function and the arguments that it requires. For example, if you typed help pop_loadset(), MATLAB would display a help text file which would tell you that the function needs a the name of a file and its path. The function would then take the following shape: EEG = pop_loadset('filename', 'S1.set');
  • Recently, EEGLAB has implemented a function to export the history of your processing session to a *.mat file. This means that for all the steps we have done so far we actually can retrieve the command line that was ran. It's not perfect, but it's a great help to quickly script stepts and customise them.
  • For example, when we loaded the *.cnt file at the beginning of our session, the menu called the function pop_loadcnt() and the function took the following form:
EEG = pop_loadcnt('/Users/pss059/Desktop/LabelsData/526.cnt' , 'dataformat', 'auto', 'memmapfile', '');

What this basically does is assign a loaded dataset into an object called EEG. EEG refers to the current dataset loaded in memory. It is a convention of EEGLAB.

Loops & hoops

The level of programming that batching requires doesn't really go much further than creating loops. Which once you've seen one you know them all.

The basic idea of a loop is to loop through a certain number of operations for a certain number of times and goes through the following logic:

  1. Declare the variable you want to loop over var=value
  2. Explain how you are looping through the variable
    1. A common one is to go through each element of the variable for length(var)
  3. List operations to be performed e.g., a=rand()
  4. end loop

*/

Here are a few basic loops: write loops later */

people=[1,0,0,1,1];
 
%lets count people
count=0;
 
for i=1:length(people)
    count=count+1;
end
 
 
%lets make it harder for us to count manually
n=1900000;
for j=1:n;
    people(j)=[rand(1)>0.2];
end
 
%lets count males and females
%males are labelled by a 1
&females are labelled by a 0
males=0;
females=0;
for k=1:length(people)
    if people(k)==1
        males=males+1;
    else
        females=females+1;
    end
end
 
%collect info in a loop
a=1;
for l=1:n
  a=a*1.2;
 
evol(l,:)=a;
end

*/ In our case, we will want to perform a series of operations which will be repeated **over participants**: * We will first "load" our participants (say their participant number –but it could be anything) <code matlab> subject={'100' '101' '103' '104'};</code> * Then we will specify how we are going through the loop. In this instance we want each instance of ''ppts'' to be passed through. The little voice in the computer goes like this: "for each instance of ppts…" <code matlab> subject={'100' '101' '103' '104'}; for i=1:length(subject) </code> * Last thing, we need make stuff happen. In this instance the first thing we will probably want to do is to load a ''*.cnt'' file. <code matlab> subject={'100' '101'}; for i=1:length(subject) EEG = doSomething(); end </code> If we run this, MATLAB will ''doSomething()'' to the object ''EEG'' for all two participants. ==== 2. Preparation of "NightCrew" script ==== The steps that we have taken so far, at least some operations, are pretty slow (ICA). Before we carry those out there is not much that we can do with the data in terms of analysis. So the plan is to run these steps at night when it doesn't matter whether we can use our computer or not. For this reason we will talk of two kinds of scripts: * **"Night Crew"**, runs at night and shouldn't include steps with which we often play around. * **"Dat Crew"**, run during the day. They're usually scripts that take no more than 5 minutes to run. It will usually includes steps which we might have to re-configurate or runs steps which give us results we need to attend to directly. Now is the time to get some serious business going on: <code matlab> rollSleeves=1 YOU=rollSleeves wait 2 seconds rollSleeves=0 YOU=rollSleeves </code> We will go through each of the GUI steps again but this time look at how they can be implemented using command lines. ===1. Load CNT=== <code matlab> EEG = pop_loadcnt([subject{i} '.cnt'], 'dataformat', 'int32'); </code> ''pop_loadcnt()'' loads a CNT file, makes an EEG structure and write it into the ''EEG'' object. ''[subject{i} '.cnt']'' is the filename (it can contain a path as well. Instead of manually writing the file name ''101.cnt'' we replace this by passing through the current value of the array ''subject''. The ''{i}'' instructs MATLAB to pull out the value equal to the cell the loop is currently reading. '''dataformat', 'int32''' are optional parameters. Here they indicate MATLAB that the file format is in 32bits. ===2. Load electrode positions, append channel for online reference, label appended channel as the reference=== <code matlab> %add electrode positions, and specify online ref EEG = pop_chanedit(EEG,'append',66,'changefield',{67 'labels' 'Cz'},... 'lookup','/Users/pss059/Documents/MATLAB/eeglab12_0_2_5b/plugins/dipfit2.2/standard_BESA/standard-10-5-cap385.elp',... 'setref',{'1:67' 'Cz'}); </code> This one line (although it looks slightly long) condenses the cumbersome first steps of re-referenceing: '''append',66'' appends a channel after channel number 66.\\ '''changefield', {67 'labels' 'Cz'}'' changes information about channel 67 namely, its label.\\ '''lookup', '/Users…cap385.elp''' looks-up locations for all electrodes in the BESA file.\\ '''setref',{'1:67' 'Cz'}'' labels Cz as the current reference to all channels.\\ One final step in that part is needed: referencing to the common average: <code matlab> %add electrode positions, and specify online ref EEG = pop_chanedit(EEG,'append',66,'changefield',{67 'labels' 'Cz'},... 'lookup','/Users/pss059/Documents/MATLAB/eeglab12_0_2_5b/plugins/dipfit2.2/standard_BESA/standard-10-5-cap385.elp',... 'setref',{'1:67' 'Cz'}); %re-reference to common average & reconstruct signal at current reference EEG = pop_reref( EEG, [],'refloc',struct('labels',{'Cz'},'type',{''},'theta',{0},'radius',{0},'X',{5.2047e-15},'Y',{0},'Z',{85},'sph_theta',{0},'sph_phi',{90},'sph_radius',{85},'urchan',{67},'ref',{'Cz'},'datachan',{0}), 'exclude',[65 66]); </code> Again this looks like a long one but we don't need to worry much: ''[]'' means "all channels" and therefore computes an average reference '''refloc'' instructs to reconstruct the signal of the online reference electrode. It takes the long ''struc()'' as input, which contains the name of the channel, the location and the fact that it is the current reference. '''exlude', [65 66]'' makes sure channels 65 66 (VEOG & HEOG) do not take part in the average reference, since these channels are not part of the scalp and would add noise to the data. ===3. Pre-epoching (file size reduction)=== <code matlab> %make epochs for the following triggers EEG = pop_epoch( EEG, { '111' '112' '113' '114' '121' '122' '123' '124' '131' '132' '133' '134' '141' '142' '143' '144' '151' '152' '153' '154' '211' '212' '213' '214' '221' '222' '223' '224' '231' '232' '233' '234' '241' '242' '243' '244' '251' '252' '253' '254' }, [-0.1 1], 'epochinfo', 'yes'); %remove baseline EEG = pop_rmbase( EEG, [-100 0]); </code> This one is easy: ''{'111' '112' … '245'}'' lists all trigger types for which we want to create epochs. ''[-0.1 1]'' min max limits (in seconds) of your epochs '''epochinfo''' is set to true and will populate the data set with the even info (you want this on). We also want to baseline correct those epochs that is what ''pop_rmbase'' does. ''[-100 0]'' sets the min max limites in MILLIseconds this time. ===4. Filtering=== <code matlab> EEG = pop_basicfilter( EEG, 1:67 , 'Cutoff', [ 0.1 30], 'Design', 'butter', 'Filter', 'bandpass', 'Order', 4 ); </code> ===5. ICA decomposition=== <code matlab> EEG = pop_runica(EEG, 'extended',1,'interupt','on'); </code> ===6. Other useful commands=== Here are some useful commands that you may want to use after some operations, like save intermediary sets for some sets (to which you think you might want to go back), or check that the set contains no problem (especially useful after modifying events and epochs). * change the name of a set <code matlab> EEG.setname = 'NewSetName'; </code> * save a set <code matlab> EEG = pop_saveset(EEG, 'filename','101.set','filepath', '/User.../setfolder/'); </code> * check set consistency <code matlab> EEG = pop_checkset(EEG); </code> <WRAP center round todo 80%> **HACK #2** {{:hacklogo2.png?nolink&40 |}}\\ \\ Now that we have brushed up a few things about loops and now that we have seen a few useful commands for EEGLAB.\\ Let's see if we can write a simple routine that **loads** a ''*.cnt'' file and **exports** it (or save it) as an EEGLAB dataset. </WRAP> <WRAP center round tip 80%> **TRY-CATCH!** One last **very handy** piece of code to know is the ''try-catch'' "loop" Whenever something goes wrong between the ''try'' and ''catch'' MATLAB will jump to the statement just after ''catch'' and will continue. You can use that to jump over a buggy dataset for example: </WRAP> *Here would be the implementation that avoids banging your head on the table 10 times because you've lost a night of processing <code matlab> subject={'100' '101' '103' '104'}; for i=1:length(subject) try EEG = pop_loadcnt([subject{i} '.cnt'], 'dataformat', 'int32'); catch disp([‘Something went wrong with participant’ subject{i} ‘ Skipping to next participant’]); end end </code> <WRAP center round todo 80%> **HACK #3** {{:hacklogo2.png?nolink&40 |}}\\ \\ Now that we have brushed up a few things about loops and now that we have every command line corresponding to our processing pipeline your task is to **write** a fully functional **Night Crew** batch. * Making sure that it cycles over participants and * that it **saves** the a set after **epoching/baseline**, and after **filtering** in case the filter or ICA step crash. * make sure your loop **doesn't get stuck** because of a buggy dataset. * save final dataset. (NOTE. when saving datasets you might want to think of a way to name the dataset with the subject information) </WRAP> */ <file matlab NightCrew.m> subject={'536', '538'}; pathname_read='/Users/pss059/Desktop/QuickTests/'; pathname_write='/Users/pss059/Desktop/QuickTests/NightCrew/'; for i=1:length(subject) fprintf('Processing Subject #%g : %s...\n', i, subject{i}); %creates the destination folder assuming you have not created it manually before %if test makes sure the folder only gets created once. if isequal(exist(pathname_write, 'dir'),7) %7 = directory display(' Destination folder exists. All Good to go!'); else [mdirstatus, mdirmessage]=mkdir(pathname_write) display(' Destination folder does not exist. Chillax! Will be created'); end %try %add electrode positions, and specify online ref EEG = pop_loadcnt([pathname_read subject{i} '.cnt'] , 'dataformat', 'int32', 'memmapfile', ''); EEG = pop_chanedit(EEG, 'append',66,'changefield',{67 'labels' 'Cz'},'lookup','/Users/pss059/Documents/MATLAB/eeglab12_0_2_5b/plugins/dipfit2.2/standard_BESA/standard-10-5-cap385.elp','setref',{'1:67' 'Cz'}); %re-reference to common average & reconstruct signal at current reference EEG = pop_reref( EEG, [],'refloc',struct('labels',{'Cz'},'type',{''},'theta',{0},'radius',{0},'X',{5.2047e-15},'Y',{0},'Z',{85},'sph_theta',{0},'sph_phi',{90},'sph_radius',{85},'urchan',{67},'ref',{'Cz'},'datachan',{0}), 'exclude',[65 66]); %make epochs (all triggers of interest individually %we will in fact comment the remove baseline step since at the minute %we just want to cut the file to reduce dimensions. EEG = pop_epoch( EEG, { '111' '112' '113' '114' '121' '122' '123' '124' '131' '132' '133' '134' '141' '142' '143' '144' '151' '152' '153' '154' '211' '212' '213' '214' '221' '222' '223' '224' '231' '232' '233' '234' '241' '242' '243' '244' '251' '252' '253' '254' }, [-0.1 1], 'epochinfo', 'yes'); %EEG = pop_rmbase( EEG, [-100 0]); %We could already delete epochs which are followed by an incorrect %response. Although I prefer to keep this for the subsequent Day Crews %EEG = pop_selectevent( EEG, 'type',1,'deleteevents','off','deleteepochs','on','invertepochs','off'); %Save set prior to filtering (in case of crash) EEG.setname = [subject{i} 'RREP']; EEG = pop_saveset( EEG, 'filename', [pathname_write subject{i} '_RREP.set']); EEG = eeg_checkset(EEG); %filter the data EEG = pop_basicfilter( EEG, 1:67 , 'Cutoff', [ 0.1 30], 'Design', 'butter', 'Filter', 'bandpass', 'Order', 4 ); %Save intermediary set in case ICA crashes EEG.setname = [subject{i} 'RREPF']; EEG = pop_saveset( EEG, 'filename', [pathname_write subject{i} '_RREPF.set']); %run ICA decomposition EEG = pop_runica(EEG, 'extended',1,'interupt','on'); %Save final set EEG.setname = [subject{i} 'RREPFICA']; EEG = pop_saveset( EEG, 'filename', [pathname_write subject{i} '_RREPFICA.set']); %Once you have fully debugged your script and that you know it goes %through without problems (Due to scripting) uncomment the following %lines. It allows you to jump participants if the sets are buggy but %won't give you error messages. %catch % disp(['%Something went wrong with participant ' subject{i} ' ! Skipping to next participant %']);

  %end

end </file>

DISCLAIMER: The tutorials provided on this wiki are not intended to compete with the tutorials written by the EEGLAB's (and other toolboxes) developers (EEGLAB website). It intends to be a condensed version for educational/reference purposes for members of the lab/department to which this workshop was given. */

eeglabsessh1b.1391446062.txt.gz · Last modified: 2014/10/08 03:14 (external edit)