forked from happynear/FaceVerification
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathJointBayesian.m
117 lines (109 loc) · 3.15 KB
/
JointBayesian.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
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
function [mappedX, mapping] = JointBayesian(X, labels)
% Joint Bayesian
% Chen D, Cao X, Wang L, et al. Bayesian face revisited: A joint formulation, ECCV 2012.
%
% programmed by happynear
% https://github.com/happynear
m = length(labels);
n = size(X,2);
% Make sure labels are nice
[classes, bar, labels] = unique(labels);
nc = length(classes);
% Intialize Sw
Sw = zeros(size(X, 2), size(X, 2));
cur = {};
withinCount = 0;
numberBuff = zeros(1000,1);
% numberInvert = zeros(1000,1);
maxNumberInOneClass = [];
for i=1:nc
% Get all instances with class i
cur{i} = X(labels == i,:);
if size(cur{i},1)>1
withinCount = withinCount + size(cur{i},1);
end;
if numberBuff(size(cur{i},1)) ==0
numberBuff(size(cur{i},1)) = 1;
maxNumberInOneClass = [maxNumberInOneClass;size(cur{i},1)];
end;
end;
disp([nc withinCount]);
fprintf('prepare done, maxNumberInOneClass=%d.\n',length(maxNumberInOneClass));
tic;
u = zeros(n,nc);
ep = zeros(n,withinCount);
nowp = 1;
% Sum over classes
for i=1:nc
% Update within-class scatter
u(:,i) = mean(cur{i},1)';
if size(cur{i},1)>1
ep(:,nowp:nowp+ size(cur{i}, 1)-1) = bsxfun(@minus,cur{i}',u(:,i));
nowp = nowp + size(cur{i}, 1);
% C = cov(cur{i});
% p = size(cur{i}, 1) / withinCount;
% Sw = Sw + (p * C);
end;
end;
Su = cov(u');
Sw = cov(ep');
% Su = u*u'/nc;
% Sw = ep*ep'/withinCount;
% Su = cov(rand(n,n));
% Sw = cov(rand(5*n,n));
fprintf('LDA matrix done.\n');
toc;
% F = inv(Sw);
% mapping.Su = Su;
% mapping.Sw = Sw;
% mapping.G = -1 .* (2 * Su + Sw) \ Su / Sw;
% mapping.A = inv(Su + Sw) - (F + mapping.G);
% mappedX = X;
% end
oldSw = Sw;
% Gs = cell(maxNumberInOneClass,1);
SuFG = cell(1000,1);
SwG = cell(1000,1);
for l=1:500
% tic;
F = inv(Sw);
ep =zeros(n,m);
nowp = 1;
for g = 1:1000
if numberBuff(g)==1
G = -1 .* (g .* Su + Sw) \ Su / Sw;
SuFG{g} = Su * (F + g.*G);
SwG{g} = Sw*G;
end;
end;
for i=1:nc
nnc = size(cur{i}, 1);
% G = Gs{nnc};
u(:,i) = sum(SuFG{nnc} * cur{i}',2);
ep(:,nowp:nowp+ size(cur{i}, 1)-1) = bsxfun(@plus,cur{i}',sum(SwG{nnc}*cur{i}',2));
nowp = nowp+ nnc;
end;
Su = cov(u');
Sw = cov(ep');
% Su = u*u'/nc;
% Sw = ep*ep'/withinCount;
fprintf('%d %f\n',l,norm(Sw - oldSw)/norm(Sw));
% toc;
if norm(Sw - oldSw)/norm(Sw)<1e-6
break;
end;
oldSw = Sw;
end;
F = inv(Sw);
mapping.G = -1 .* (2 * Su + Sw) \ Su / Sw;
mapping.A = inv(Su + Sw) - (F + mapping.G);
mapping.Sw = Sw;
mapping.Su = Su;
% mapping.U = chol(-G,'upper');
% mapping.COEFF = COEFF;
% mapping.y = mapping.U * X';
mapping.c = zeros(m,1);
for i = 1:m
mapping.c(i) = X(i,:) * mapping.A * X(i,:)';
end;
mappedX = X;