Mercurial > hg > camir-aes2014
comparison toolboxes/FullBNT-1.0.7/bnt/potentials/@cgpot/marginalize_pot.m @ 0:e9a9cd732c1e tip
first hg version after svn
author | wolffd |
---|---|
date | Tue, 10 Feb 2015 15:05:51 +0000 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
-1:000000000000 | 0:e9a9cd732c1e |
---|---|
1 function smallpot = marginalize_pot(bigpot, keep, maximize, useC) | |
2 % MARGINALIZE_POT Marginalize a cgpot onto a smaller domain. | |
3 % smallpot = marginalize_pot(bigpot, keep, maximize, useC) | |
4 % | |
5 % If maximize = 1, we raise an error. | |
6 % useC is ignored. | |
7 | |
8 if nargin < 3, maximize = 0; end | |
9 assert(~maximize); | |
10 | |
11 | |
12 sumover = mysetdiff(bigpot.domain, keep); | |
13 csumover = myintersect(sumover, bigpot.cdom); | |
14 dsumover = myintersect(sumover, bigpot.ddom); | |
15 dkeep = myintersect(keep, bigpot.ddom); | |
16 ckeep = myintersect(keep, bigpot.cdom); | |
17 %ns = sparse(1, max(bigpot.domain)); % must be full, so I is an integer | |
18 ns = zeros(1, max(bigpot.domain)); | |
19 ns(bigpot.ddom) = bigpot.dsizes; | |
20 ns(bigpot.cdom) = bigpot.csizes; | |
21 | |
22 % sum(ns(csumover))==0 is like isempty(csumover) but handles observed nodes. | |
23 % Similarly, prod(ns(dsumover))==1 is like isempty(dsumover) | |
24 | |
25 % Marginalize the cts parts. | |
26 % If we are in canonical form, we stay that way, since moment form might not exist. | |
27 % Besides, we would like to minimize the number of conversions. | |
28 if sum(ns(csumover)) > 0 | |
29 if bigpot.subtype == 'm' | |
30 for i=1:bigpot.dsize | |
31 bigpot.mom{i} = marginalize_pot(bigpot.mom{i}, ckeep); | |
32 end | |
33 else | |
34 for i=1:bigpot.dsize | |
35 bigpot.can{i} = marginalize_pot(bigpot.can{i}, ckeep); | |
36 end | |
37 end | |
38 end | |
39 | |
40 % If we are not marginalizing over any discrete nodes, we are done. | |
41 if prod(ns(dsumover))==1 | |
42 smallpot = cgpot(dkeep, ckeep, ns, bigpot.can, bigpot.mom, bigpot.subtype); | |
43 return; | |
44 end | |
45 | |
46 % To marginalize the discrete parts, we partition the cts parts into those that depend | |
47 % on dkeep (i) and those that depend on on dsumover (j). | |
48 | |
49 I = prod(ns(dkeep)); | |
50 J = prod(ns(dsumover)); | |
51 C = sum(ns(ckeep)); | |
52 sum_map = find_equiv_posns(dsumover, bigpot.ddom); | |
53 keep_map = find_equiv_posns(dkeep, bigpot.ddom); | |
54 iv = zeros(1, length(bigpot.ddom)); % index vector | |
55 | |
56 % If in canonical form, marginalize if possible, else convert to moment form. | |
57 if 0 & bigpot.subtype == 'c' | |
58 p1 = zeros(I,J); | |
59 h1 = zeros(C,J,I); | |
60 K1 = zeros(C,C,J,I); | |
61 for i=1:I | |
62 keep_iv = ind2subv(ns(dkeep), i); | |
63 iv(keep_map) = keep_iv; | |
64 for j=1:J | |
65 sum_iv = ind2subv(ns(dsumover), j); | |
66 iv(sum_map) = sum_iv; | |
67 k = subv2ind(ns(bigpot.ddom), iv); | |
68 can = struct(bigpot.can{k}); % violate object privacy | |
69 p1(i,j) = exp(can.g); | |
70 if C > 0 % so mu1 and Sigma1 are non-empty | |
71 h1(:,j,i) = can.h; | |
72 K1(:,:,j,i) = can.K; | |
73 end | |
74 end | |
75 end | |
76 | |
77 % If the cts parts do not depend on j, we can just marginalize the weighting coefficient g. | |
78 jdepends = 0; | |
79 for i=1:I | |
80 for j=2:J | |
81 if ~approxeq(h1(:,j,i), h1(:,1,i)) | ~approxeq(K1(:,:,j,i), K1(:,:,1,i)) | |
82 jdepends = 1; | |
83 break | |
84 end | |
85 end | |
86 end | |
87 | |
88 if ~jdepends | |
89 %g2 = log(sum(p1, 2)); | |
90 g2 = zeros(I,1); | |
91 for i=1:I | |
92 s = sum(p1(i,:)); | |
93 if s > 0 | |
94 g2(i) = log(s); | |
95 end | |
96 end | |
97 h2 = h1; | |
98 K2 = K1; | |
99 can = cell(1,I); | |
100 j = 1; % arbitrary | |
101 for i=1:I | |
102 can{i} = cpot(ckeep, ns(ckeep), g2(i), h2(:,j,i), K2(:,:,j,i)); | |
103 end | |
104 smallpot = cgpot(dkeep, ckeep, ns, can, [], 'c'); | |
105 return; | |
106 else | |
107 % Since the cts parts depend on j, we must convert to moment form | |
108 bigpot = cg_can_to_mom(bigpot); | |
109 end | |
110 end | |
111 | |
112 | |
113 % Marginalize in moment form | |
114 bigpot = cg_can_to_mom(bigpot); | |
115 | |
116 % Now partition the moment components. | |
117 T1 = zeros(I,J); | |
118 mu1 = zeros(C,J,I); | |
119 Sigma1 = zeros(C,C,J,I); | |
120 for i=1:I | |
121 keep_iv = ind2subv(ns(dkeep), i); | |
122 iv(keep_map) = keep_iv; | |
123 for j=1:J | |
124 sum_iv = ind2subv(ns(dsumover), j); | |
125 iv(sum_map) = sum_iv; | |
126 k = subv2ind(ns(bigpot.ddom), iv); | |
127 mom = struct(bigpot.mom{k}); % violate object privacy | |
128 T1(i,j) = exp(mom.logp); | |
129 if C > 0 % so mu1 and Sigma1 are non-empty | |
130 mu1(:,j,i) = mom.mu; | |
131 Sigma1(:,:,j,i) = mom.Sigma; | |
132 end | |
133 end | |
134 end | |
135 | |
136 % Collapse the mixture of Gaussians | |
137 coef = mk_stochastic(T1); % coef must be convex combination | |
138 T2 = sum(T1,2); | |
139 T2 = T2 + (T2==0)*eps; | |
140 %if C > 0, disp('collapsing onto '); disp(leep); end | |
141 mu = []; | |
142 Sigma = []; | |
143 mom = cell(1,I); | |
144 for i=1:I | |
145 if C > 0 | |
146 [mu, Sigma] = collapse_mog(mu1(:,:,i), Sigma1(:,:,:,i), coef(i,:)); | |
147 end | |
148 logp = log(T2(i)); | |
149 mom{i} = mpot(ckeep, ns(ckeep), logp, mu, Sigma); | |
150 end | |
151 | |
152 smallpot = cgpot(dkeep, ckeep, ns, [], mom, 'm'); | |
153 |