braindecode 0.1.4.1__tar.gz → 0.1.4.2__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/Braindecode.egg-info/PKG-INFO +1 -1
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/Braindecode.egg-info/SOURCES.txt +1 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/PKG-INFO +1 -1
- Braindecode-0.1.4.2/braindecode/models/deep4.py +159 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/models/shallow_fbcsp.py +4 -2
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/torch_ext/functions.py +4 -0
- Braindecode-0.1.4.2/docs/notebooks/BBCI_Data.ipynb +683 -0
- Braindecode-0.1.4.2/docs/notebooks/BBCI_Data_Start_Stop.ipynb +877 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/docs/notebooks/Cropped_Decoding.ipynb +65 -65
- Braindecode-0.1.4.2/docs/notebooks/Experiment_Class.ipynb +819 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/docs/source/braindecode.models.rst +8 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/setup.py +1 -1
- Braindecode-0.1.4.1/docs/notebooks/BBCI_Data.ipynb +0 -663
- Braindecode-0.1.4.1/docs/notebooks/BBCI_Data_Start_Stop.ipynb +0 -877
- Braindecode-0.1.4.1/docs/notebooks/Experiment_Class.ipynb +0 -795
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/Braindecode.egg-info/dependency_links.txt +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/Braindecode.egg-info/not-zip-safe +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/Braindecode.egg-info/requires.txt +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/Braindecode.egg-info/top_level.txt +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/LICENSE.txt +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/MANIFEST.in +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/README.rst +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/__init__.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/datasets/__init__.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/datasets/bbci.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/datasets/multiple.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/datautil/__init__.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/datautil/iterators.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/datautil/signal_target.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/datautil/signalproc.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/datautil/splitters.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/datautil/trial_segment.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/datautil/util.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/experiments/__init__.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/experiments/experiment.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/experiments/monitors.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/experiments/stopcriteria.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/mne_ext/__init__.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/mne_ext/signalproc.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/models/__init__.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/torch_ext/__init__.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/torch_ext/constraints.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/torch_ext/losses.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/torch_ext/modules.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/torch_ext/util.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/braindecode/util.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/docs/Makefile +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/docs/conf.py +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/docs/index.rst +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/docs/notebooks/TrialWise_Decoding.ipynb +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/docs/source/braindecode.datasets.rst +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/docs/source/braindecode.datautil.rst +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/docs/source/braindecode.experiments.rst +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/docs/source/braindecode.mne_ext.rst +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/docs/source/braindecode.rst +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/docs/source/braindecode.torch_ext.rst +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/docs/source/modules.rst +0 -0
- {Braindecode-0.1.4.1 → Braindecode-0.1.4.2}/setup.cfg +0 -0
|
@@ -27,6 +27,7 @@ braindecode/experiments/stopcriteria.py
|
|
|
27
27
|
braindecode/mne_ext/__init__.py
|
|
28
28
|
braindecode/mne_ext/signalproc.py
|
|
29
29
|
braindecode/models/__init__.py
|
|
30
|
+
braindecode/models/deep4.py
|
|
30
31
|
braindecode/models/shallow_fbcsp.py
|
|
31
32
|
braindecode/torch_ext/__init__.py
|
|
32
33
|
braindecode/torch_ext/constraints.py
|
|
@@ -0,0 +1,159 @@
|
|
|
1
|
+
import numpy as np
|
|
2
|
+
from torch import nn
|
|
3
|
+
from torch.nn import init
|
|
4
|
+
from torch.nn.functional import elu
|
|
5
|
+
from braindecode.torch_ext.modules import Expression
|
|
6
|
+
from braindecode.torch_ext.functions import identity
|
|
7
|
+
from braindecode.torch_ext.util import np_to_var
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
class Deep4Net(object):
|
|
11
|
+
def __init__(self, in_chans,
|
|
12
|
+
n_classes,
|
|
13
|
+
input_time_length,
|
|
14
|
+
final_conv_length,
|
|
15
|
+
n_filters_time=25,
|
|
16
|
+
n_filters_spat=25,
|
|
17
|
+
filter_time_length=10,
|
|
18
|
+
pool_time_length=3,
|
|
19
|
+
pool_time_stride=3,
|
|
20
|
+
num_filters_2=50,
|
|
21
|
+
filter_length_2=10,
|
|
22
|
+
num_filters_3=100,
|
|
23
|
+
filter_length_3=10,
|
|
24
|
+
num_filters_4=200,
|
|
25
|
+
filter_length_4=10,
|
|
26
|
+
first_nonlin=elu,
|
|
27
|
+
first_pool_mode='max',
|
|
28
|
+
first_pool_nonlin=identity,
|
|
29
|
+
later_nonlin=elu,
|
|
30
|
+
later_pool_mode='max',
|
|
31
|
+
later_pool_nonlin=identity,
|
|
32
|
+
drop_prob=0.5,
|
|
33
|
+
double_time_convs=False,
|
|
34
|
+
split_first_layer=True,
|
|
35
|
+
batch_norm=True,
|
|
36
|
+
batch_norm_alpha=0.1):
|
|
37
|
+
if final_conv_length == 'auto':
|
|
38
|
+
assert input_time_length is not None
|
|
39
|
+
|
|
40
|
+
self.__dict__.update(locals())
|
|
41
|
+
del self.self
|
|
42
|
+
|
|
43
|
+
def create_network(self):
|
|
44
|
+
pool_class_dict = dict(max=nn.MaxPool2d, mean=nn.AvgPool2d)
|
|
45
|
+
first_pool_class = pool_class_dict[self.first_pool_mode]
|
|
46
|
+
later_pool_class = pool_class_dict[self.later_pool_mode]
|
|
47
|
+
model = nn.Sequential()
|
|
48
|
+
if self.split_first_layer:
|
|
49
|
+
model.add_module('dimshuffle',
|
|
50
|
+
Expression(lambda x: x.permute(0, 3, 2, 1)))
|
|
51
|
+
model.add_module('conv_time', nn.Conv2d(1, self.n_filters_time,
|
|
52
|
+
(
|
|
53
|
+
self.filter_time_length, 1),
|
|
54
|
+
stride=1, ))
|
|
55
|
+
model.add_module('conv_spat',
|
|
56
|
+
nn.Conv2d(self.n_filters_time, self.n_filters_spat,
|
|
57
|
+
(1, self.in_chans), stride=1,
|
|
58
|
+
bias=not self.batch_norm))
|
|
59
|
+
n_filters_conv = self.n_filters_spat
|
|
60
|
+
else:
|
|
61
|
+
model.add_module('conv_time',
|
|
62
|
+
nn.Conv2d(self.in_chans, self.n_filters_time,
|
|
63
|
+
(self.filter_time_length, 1),
|
|
64
|
+
stride=1,
|
|
65
|
+
bias=not self.batch_norm))
|
|
66
|
+
n_filters_conv = self.n_filters_time
|
|
67
|
+
if self.batch_norm:
|
|
68
|
+
model.add_module('bnorm',
|
|
69
|
+
nn.BatchNorm2d(n_filters_conv,
|
|
70
|
+
momentum=self.batch_norm_alpha,
|
|
71
|
+
affine=True,
|
|
72
|
+
eps=1e-5),)
|
|
73
|
+
model.add_module('conv_nonlin', Expression(self.first_nonlin))
|
|
74
|
+
model.add_module('pool',
|
|
75
|
+
first_pool_class(
|
|
76
|
+
kernel_size=(self.pool_time_length, 1),
|
|
77
|
+
stride=(self.pool_time_stride, 1)))
|
|
78
|
+
model.add_module('pool_nonlin', Expression(self.first_pool_nonlin))
|
|
79
|
+
|
|
80
|
+
def add_conv_pool_block(model, num_filters_before,
|
|
81
|
+
num_filters, filter_length, block_nr):
|
|
82
|
+
suffix = '_{:d}'.format(block_nr)
|
|
83
|
+
model.add_module('drop' + suffix,
|
|
84
|
+
nn.Dropout(p=self.drop_prob))
|
|
85
|
+
model.add_module('conv' + suffix.format(block_nr),
|
|
86
|
+
nn.Conv2d(num_filters_before, num_filters,
|
|
87
|
+
(filter_length, 1),
|
|
88
|
+
stride=1, bias=not self.batch_norm))
|
|
89
|
+
if self.batch_norm:
|
|
90
|
+
model.add_module('bnorm' + suffix,
|
|
91
|
+
nn.BatchNorm2d(num_filters,
|
|
92
|
+
momentum=self.batch_norm_alpha,
|
|
93
|
+
affine=True,
|
|
94
|
+
eps=1e-5))
|
|
95
|
+
model.add_module('nonlin' + suffix,
|
|
96
|
+
Expression(self.later_nonlin))
|
|
97
|
+
|
|
98
|
+
model.add_module('pool' + suffix,
|
|
99
|
+
later_pool_class(
|
|
100
|
+
kernel_size=(self.pool_time_length, 1),
|
|
101
|
+
stride=(self.pool_time_stride, 1)))
|
|
102
|
+
model.add_module('pool_nonlin' + suffix,
|
|
103
|
+
Expression(self.later_pool_nonlin))
|
|
104
|
+
|
|
105
|
+
add_conv_pool_block(model, n_filters_conv, self.num_filters_2,
|
|
106
|
+
self.filter_length_2, 2)
|
|
107
|
+
add_conv_pool_block(model, self.num_filters_2, self.num_filters_3,
|
|
108
|
+
self.filter_length_3, 3)
|
|
109
|
+
add_conv_pool_block(model, self.num_filters_3, self.num_filters_4,
|
|
110
|
+
self.filter_length_4, 4)
|
|
111
|
+
|
|
112
|
+
|
|
113
|
+
if self.final_conv_length == 'auto':
|
|
114
|
+
out = model(np_to_var(np.ones(
|
|
115
|
+
(1, self.in_chans, self.input_time_length,1),
|
|
116
|
+
dtype=np.float32)))
|
|
117
|
+
n_out_time = out.cpu().data.numpy().shape[2]
|
|
118
|
+
self.final_conv_length = n_out_time
|
|
119
|
+
model.add_module('conv_classifier',
|
|
120
|
+
nn.Conv2d(self.num_filters_4, self.n_classes,
|
|
121
|
+
(self.final_conv_length, 1), bias=True))
|
|
122
|
+
model.add_module('softmax', nn.LogSoftmax())
|
|
123
|
+
# remove empty dim at end and potentially remove empty time dim
|
|
124
|
+
# do not just use squeeze as we never want to remove first dim
|
|
125
|
+
def squeeze_output(x):
|
|
126
|
+
assert x.size()[3] == 1
|
|
127
|
+
x = x[:,:,:,0]
|
|
128
|
+
if x.size()[2] == 1:
|
|
129
|
+
x = x[:,:,0]
|
|
130
|
+
return x
|
|
131
|
+
model.add_module('squeeze', Expression(squeeze_output))
|
|
132
|
+
|
|
133
|
+
# Initialization, xavier is same as in our paper...
|
|
134
|
+
# was default from lasagne
|
|
135
|
+
init.xavier_uniform(model.conv_time.weight, gain=1)
|
|
136
|
+
# maybe no bias in case of no split layer and batch norm
|
|
137
|
+
if self.split_first_layer or (not self.batch_norm):
|
|
138
|
+
init.constant(model.conv_time.bias, 0)
|
|
139
|
+
if self.split_first_layer:
|
|
140
|
+
init.xavier_uniform(model.conv_spat.weight, gain=1)
|
|
141
|
+
if not self.batch_norm:
|
|
142
|
+
init.constant(model.conv_spat.bias, 0)
|
|
143
|
+
param_dict = dict(list(model.named_parameters()))
|
|
144
|
+
for block_nr in range(2,5):
|
|
145
|
+
conv_weight = param_dict['conv_{:d}.weight'.format(block_nr)]
|
|
146
|
+
init.xavier_uniform(conv_weight, gain=1)
|
|
147
|
+
if not self.batch_norm:
|
|
148
|
+
conv_bias = param_dict['conv_{:d}.bias'.format(block_nr)]
|
|
149
|
+
init.constant(conv_bias, 0)
|
|
150
|
+
else:
|
|
151
|
+
bnorm_weight = param_dict['bnorm_{:d}.weight'.format(block_nr)]
|
|
152
|
+
bnorm_bias = param_dict['bnorm_{:d}.bias'.format(block_nr)]
|
|
153
|
+
init.constant(bnorm_weight, 1)
|
|
154
|
+
init.constant(bnorm_bias, 0)
|
|
155
|
+
|
|
156
|
+
init.xavier_uniform(model.conv_classifier.weight, gain=1)
|
|
157
|
+
init.constant(model.conv_classifier.bias, 0)
|
|
158
|
+
|
|
159
|
+
return model
|
|
@@ -8,7 +8,6 @@ from braindecode.torch_ext.util import np_to_var
|
|
|
8
8
|
|
|
9
9
|
|
|
10
10
|
class ShallowFBCSPNet(object):
|
|
11
|
-
# TODO: auto final dense length for shallow
|
|
12
11
|
def __init__(self, in_chans,
|
|
13
12
|
n_classes,
|
|
14
13
|
input_time_length=None,
|
|
@@ -25,7 +24,7 @@ class ShallowFBCSPNet(object):
|
|
|
25
24
|
batch_norm=True,
|
|
26
25
|
batch_norm_alpha=0.1,
|
|
27
26
|
drop_prob=0.5):
|
|
28
|
-
if final_conv_length == '
|
|
27
|
+
if final_conv_length == 'auto':
|
|
29
28
|
assert input_time_length is not None
|
|
30
29
|
self.__dict__.update(locals())
|
|
31
30
|
del self.self
|
|
@@ -92,6 +91,9 @@ class ShallowFBCSPNet(object):
|
|
|
92
91
|
init.xavier_uniform(model.conv_spat.weight, gain=1)
|
|
93
92
|
if not self.batch_norm:
|
|
94
93
|
init.constant(model.conv_spat.bias, 0)
|
|
94
|
+
else:
|
|
95
|
+
init.constant(model.bnorm.weight, 1)
|
|
96
|
+
init.constant(model.bnorm.bias, 0)
|
|
95
97
|
init.xavier_uniform(model.conv_classifier.weight, gain=1)
|
|
96
98
|
init.constant(model.conv_classifier.bias, 0)
|
|
97
99
|
|