-
Notifications
You must be signed in to change notification settings - Fork 4
/
Copy pathFclust_corr.m
102 lines (92 loc) · 3.74 KB
/
Fclust_corr.m
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
%Calculate cluster correction for a F-observed and the permutation
%distribution
%
%EXAMPLE USAGE
% >> [h, p, clust_info, est_alpha] = Fclust_corr(F_obs, F_dist, 0.05, chan_hood, 3.84)
%
%REQUIRED INPUTS
% F_obs - An electrode x time points array of observed F-values
% F-dist - A permutation x electrode x time point array of the
% permutation F-distribution
% alpha - Alpha level to use for hypothesis test
% chan_hood - A symmetric 2d matrix indicating which channels are
% neighbors with other channels. If chan_hood(a,b)=1,
% then Channel A and B are neighbors. This is produced by the
% function spatial_neighbors.m.
% thresh_F - F-statistic threshold for inclusion in cluster
%
%OUTPUT
% h - electrode x time point array indicating which locations
% are part of a statistically significant cluster
% p - electrode x time point array of p-values
% clust_info - struct containing information about each cluster
% est_alpha - estimated achieved alpha level of the test; may not be
% accurate if F_dist was generated by an approximate
% permutation method
%
%
%VERSION DATE: 4 March 2020
%AUTHOR: Eric Fields
%
%NOTE: This function is provided "as is" and any express or implied warranties
%are disclaimed.
%Copyright (c) 2017-2019, Eric Fields
%All rights reserved.
%This code is free and open source software made available under the 3-clause BSD license.
function [h, p, clust_info, est_alpha] = Fclust_corr(F_obs, F_dist, alpha, chan_hood, thresh_F)
global VERBLEVEL
if VERBLEVEL
fprintf('Calculating clusters . . . ')
end
if ~isequal(chan_hood, chan_hood')
error('Your chan_hood matrix is not symmetric')
end
%Some useful numbers
[n_perm, n_electrodes, n_time_pts] = size(F_dist);
%Find clusters and cluster mass distribution
clust_mass_dist = zeros(n_perm, 1);
for i = 1:n_perm
F = reshape(F_dist(i, :, :), [n_electrodes, n_time_pts]);
%Find clusters in F
[clust_ids, n_clust] = find_clusters(F, thresh_F, chan_hood, 1);
%Save observed data
if i == 1
clust_ids_obs = clust_ids;
n_clust_obs = n_clust;
end
%Find largest cluster mass for this permutation
for c = 1:n_clust
use_mass = sum(F(clust_ids == c));
if use_mass > clust_mass_dist(i)
clust_mass_dist(i) = use_mass;
end
end
end
%Get cluster mass critical value
clust_mass_dist = sort(clust_mass_dist);
clust_mass_crit = clust_mass_dist(ceil((1-alpha) * n_perm));
%Find cluster mass for each observed cluster and compare to critical
%value
clust_mass_obs = NaN(1, n_clust_obs);
clust_pval = NaN(1, n_clust_obs);
null_test = false(1, n_clust_obs);
p = ones(n_electrodes, n_time_pts);
for c = 1:n_clust_obs
clust_mass_obs(c) = sum(F_obs(clust_ids_obs == c));
if clust_mass_obs(c) > clust_mass_crit
null_test(c) = true;
end
clust_pval(c) = mean(clust_mass_dist >= clust_mass_obs(c));
p(clust_ids_obs == c) = clust_pval(c);
end
h = (p <= alpha);
est_alpha = mean(clust_mass_dist>clust_mass_crit);
if VERBLEVEL
fprintf('DONE\n');
fprintf('Estimated alpha level is %f\n', est_alpha);
end
clust_info = struct('null_test', null_test, ...
'pval', clust_pval, ...
'clust_mass', clust_mass_obs, ...
'clust_ids', clust_ids_obs);
end