0001 function metropolis(xparam1,vv,gend,data,rawdata,mh_bounds)
0002
0003 global M_ oo_ options_ bayestopt_ estim_params_
0004
0005 bayestopt_.penalty = 1e8;
0006
0007 MhDirectoryName = CheckPath('metropolis');
0008
0009 nblck = options_.mh_nblck;
0010 nruns = ones(nblck,1)*options_.mh_replic;
0011 npar = length(xparam1);
0012 MAX_nruns = ceil(options_.MaxNumberOfBytes/(npar+2)/8);
0013 d = chol(vv);
0014 options_.lik_algo = 1;
0015 OpenOldFile = ones(nblck,1);
0016
0017 if options_.load_mh_file == 0
0018
0019
0020 if nblck > 1
0021 disp('MH: Multiple chains mode.')
0022 else
0023 disp('MH: One Chain mode.')
0024 end
0025
0026 files = dir([ MhDirectoryName '/' M_.fname '_mh*_blck*.mat']);
0027 if length(files)
0028 delete([ MhDirectoryName '/' M_.fname '_mh*_blck*.mat']);
0029 disp('MH: Old _mh files succesfully erased!')
0030 end
0031
0032 if nblck > 1
0033 disp('MH: Searching for initial values...')
0034 ix2 = zeros(nblck,npar);
0035 ilogpo2 = zeros(nblck,1);
0036 for j=1:nblck
0037 validate = 0;
0038 init_iter = 0;
0039 trial = 1;
0040 while validate == 0 & trial <= 10
0041 candidate = options_.mh_init_scale*randn(1,npar)*d + transpose(xparam1);
0042 if all(candidate' > mh_bounds(:,1)) & all(candidate' < mh_bounds(:,2))
0043 ix2(j,:) = candidate;
0044 ilogpo2(j) = -DsgeLikelihood(ix2(j,:)',gend,data);
0045 j = j+1;
0046 validate = 1;
0047 end
0048 init_iter = init_iter + 1;
0049 if init_iter > 100 & validate == 0
0050 disp(['MH: I couldn''t get a valid initial value in 100 trials.'])
0051 disp(['MH: You should Reduce mh_init_scale...'])
0052 disp(sprintf('MH: Parameter mh_init_scale is equal to %f.',options_.mh_init_scale))
0053 options_.mh_init_scale = input('MH: Enter a new value... ');
0054 trial = trial+1;
0055 end
0056 end
0057 if trial > 10 & ~validate
0058 disp(['MH: I''m unable to find a starting value for block ' int2str(j)])
0059 return
0060 end
0061 end
0062 disp('MH: Initial values found!')
0063 disp(' ')
0064 else
0065 candidate = transpose(xparam1);
0066 if all(candidate' > mh_bounds(:,1)) & all(candidate' < mh_bounds(:,2))
0067 ix2 = candidate;
0068 ilogpo2 = -DsgeLikelihood(ix2',gend,data);
0069 disp('MH: Initialization at the posterior mode.')
0070 disp(' ')
0071 else
0072 disp('MH: Initialization failed...')
0073 disp('MH: The posterior mode lies outside the prior bounds.')
0074 return
0075 end
0076 end
0077 fblck = 1;
0078 fline = ones(nblck,1);
0079 NewFile = ones(nblck,1);
0080
0081 file = dir([MhDirectoryName '/' M_.fname '_mh_history.mat']);
0082 if length(files)
0083 delete([ MhDirectoryName '/' M_.fname '_mh_history.mat']);
0084 disp('MH: Old mh_history file succesfully erased!')
0085 end
0086 AnticipatedNumberOfFiles = floor(nruns(1)/MAX_nruns);
0087 AnticipatedNumberOfLinesInTheLastFile = nruns(1) - AnticipatedNumberOfFiles*MAX_nruns;
0088 record.Nblck = nblck;
0089 record.MhDraws = zeros(1,3);
0090 record.MhDraws(1,1) = nruns(1);
0091 record.MhDraws(1,2) = AnticipatedNumberOfFiles+1;
0092 record.MhDraws(1,3) = AnticipatedNumberOfLinesInTheLastFile;
0093 record.AcceptationRates = zeros(1,nblck);
0094 record.Seeds.Normal = randn('state');
0095 record.Seeds.Unifor = rand('state');
0096 record.InitialParameters = ix2;
0097 record.InitialLogLiK = ilogpo2;
0098 record.LastParameters = zeros(nblck,npar);
0099 record.LastLogLiK = zeros(nblck,1);
0100 record.LastFileNumber = AnticipatedNumberOfFiles+1;
0101 record.LastLineNumber = AnticipatedNumberOfLinesInTheLastFile;
0102 save([MhDirectoryName '/' M_.fname '_mh_history'],'record');
0103 elseif options_.load_mh_file == 1
0104 disp('MH: I''m loading past metropolis-hastings simulations...')
0105 file = dir([ MhDirectoryName '/' M_.fname '_mh_history.mat' ]);
0106 files = dir([ MhDirectoryName '/' M_.fname '_mh*.mat']);
0107 if ~length(files)
0108 disp('MH:: FAILURE! there is no MH file to load here!')
0109 return
0110 end
0111 if ~length(file)
0112 disp('MH:: FAILURE! there is no MH-history file!')
0113 return
0114 else
0115 load([ MhDirectoryName '/' M_.fname '_mh_history'])
0116 end
0117 past_number_of_blocks = record.Nblck;
0118 if past_number_of_blocks ~= nblck
0119 disp('MH:: The specified number of blocks doesn''t match with the previous number of blocks!')
0120 disp(['MH:: You declared ' int2str(nblck) ' blocks, but the previous number of blocks was ' int2str(past_number_of_blocks) '.'])
0121 disp(['MH:: I will run the Metropolis-Hastings with ' int2str(past_number_of_blocks) ' blocks.' ])
0122 nblck = past_number_of_blocks;
0123 options_.mh_nblck = nblck;
0124 end
0125
0126
0127 LastFileNumber = record.LastFileNumber;
0128 LastLineNumber = record.LastLineNumber;
0129 if LastLineNumber < MAX_nruns
0130 NewFile = ones(nblck,1)*LastFileNumber;
0131 else
0132 NewFile = ones(nblck,1)*(LastFileNumber+1);
0133 end
0134 ilogpo2 = record.LastLogLiK;
0135 ix2 = record.LastParameters;
0136 fblck = 1;
0137 fline = ones(nblck,1)*(LastLineNumber+1);
0138 NumberOfPreviousSimulations = sum(record.MhDraws(:,1),1);
0139 record.MhDraws = [record.MhDraws;zeros(1,3)];
0140 NumberOfDrawsWrittenInThePastLastFile = MAX_nruns - LastLineNumber;
0141 NumberOfDrawsToBeSaved = nruns(1) - NumberOfDrawsWrittenInThePastLastFile;
0142 AnticipatedNumberOfFiles = floor(NumberOfDrawsToBeSaved/MAX_nruns);
0143 AnticipatedNumberOfLinesInTheLastFile = NumberOfDrawsToBeSaved - AnticipatedNumberOfFiles*MAX_nruns;
0144 record.LastFileNumber = LastFileNumber + AnticipatedNumberOfFiles + 1;
0145 record.LastLineNumber = AnticipatedNumberOfLinesInTheLastFile;
0146 record.MhDraws(end,1) = nruns(1);
0147 record.MhDraws(end,2) = AnticipatedNumberOfFiles+1;
0148 record.MhDraws(end,3) = AnticipatedNumberOfLinesInTheLastFile;
0149 randn('state',record.Seeds.Normal);
0150 rand('state',record.Seeds.Unifor);
0151 save([MhDirectoryName '/' M_.fname '_mh_history'],'record');
0152 disp(['MH: ... It''s done. I''ve loaded ' int2str(NumberOfPreviousSimulations) ' simulations.'])
0153 disp(' ')
0154 elseif options_.load_mh_file == -1
0155
0156
0157 disp('MH: Recover mode!')
0158 disp(' ')
0159 file = dir([MhDirectoryName '/' M_.fname '_mh_history.mat']);
0160 if ~length(file)
0161 disp('MH:: FAILURE! there is no MH-history file!')
0162 return
0163 else
0164 load([ MhDirectoryName '/' M_.fname '_mh_history'])
0165 end
0166 nblck = record.Nblck;
0167 options_.mh_nblck = nblck;
0168 if size(record.MhDraws,1) == 1
0169 OldMh = 0;
0170 else
0171 OldMh = 1;
0172 end
0173
0174 if OldMh
0175 ilogpo2 = record.LastLogLiK;
0176 ix2 = record.LastParameters;
0177 else
0178 ilogpo2 = record.InitialLogLiK;
0179 ix2 = record.InitialParameters;
0180 end
0181
0182 if OldMh
0183 LastLineNumberInThePreviousMh = record.MhDraws(end-1,3);
0184 LastFileNumberInThePreviousMh = sum(record.MhDraws(1:end-1,2),1);
0185 if LastLineNumberInThePreviousMh < MAX_nruns
0186 NewFile = ones(nblck,1)*LastFileNumberInThePreviousMh;
0187 else
0188 NewFile = ones(nblck,1)*(LastFileNumberInThePreviousMh+1);
0189 end
0190 else
0191 NewFile = ones(nblck,1);
0192 end
0193
0194 if OldMh
0195 fline = ones(nblck,1)*(record.MhDraws(end-1,3)+1);
0196 else
0197 fline = ones(nblck,1);
0198 end
0199
0200 fblck = 1;
0201
0202 ExpectedNumberOfMhFilesPerBlock = sum(record.MhDraws(:,2),1);
0203 ExpectedNumberOfMhFiles = ExpectedNumberOfMhFilesPerBlock*nblck;
0204
0205 AllMhFiles = dir([MhDirectoryName '/' M_.fname '_mh*_blck*.mat']);
0206 TotalNumberOfMhFiles = length(AllMhFiles);
0207
0208 NumberOfMhFilesPerBlock = zeros(nblck,1);
0209 for i = 1:nblck
0210 BlckMhFiles = dir([ MhDirectoryName '/' M_.fname '_mh*_blck' int2str(i) '.mat']);
0211 NumberOfMhFilesPerBlock(i) = length(BlckMhFiles);
0212 end
0213 tmp = NumberOfMhFilesPerBlock(1); b = 1;
0214
0215 CrashedBlck = 1;
0216 while b <= nblck
0217 if NumberOfMhFilesPerBlock(b) < ExpectedNumberOfMhFilesPerBlock
0218 CrashedBlck = b;
0219 break
0220 end
0221 b = b+1;
0222 end
0223
0224 fblck = CrashedBlck;
0225
0226 NumberOfSavedMhFilesInTheCrashedBlck = ...
0227 NumberOfMhFilesPerBlock(CrashedBlck);
0228
0229
0230 if OldMh
0231 ante = sum(record.MhDraws(1:end-1,2),1);
0232 load([MhDirectoryName '/' M_.fname '_mh' int2str(ante) '_blck' int2str(CrashedBlck) '.mat'],'logpo2');
0233 if length(logpo2) == MAX_nruns
0234 IsTheLastFileOfThePreviousMhFull = 1;
0235 else
0236 IsTheLastFileOfThePreviousMhFull = 0;
0237 end
0238 else
0239 ante = 0;
0240 IsTheLastFileOfThePreviousMhFull = 1;
0241 end
0242 if ~IsTheLastFileOfThePreviousMhFull
0243 MhFileExist = 1;
0244 MhFileNumber = ante;
0245 while MhFileExist
0246 MhFileNumber = MhFileNumber + 1;
0247 if ~exist([MhDirectoryName '/' M_.fname '_mh' int2str(MhFileNumber) '_blck' int2str(CrashedBlck) '.mat'])
0248 MhFileExist = 0;
0249 end
0250 end
0251
0252
0253
0254
0255
0256
0257 NumberOfCompletedMhFiles = (MhFileNumber-1)-ante;
0258
0259 if OldMh
0260 reste = MAX_nruns-record.MhDraws(end-1,3);
0261 else
0262 reste = 0
0263 end
0264 NumberOfSavedDraws = MAX_nruns*(NumberOfCompletedMhFiles) + reste;
0265
0266 nruns(CrashedBlck) = nruns(CrashedBlck)-NumberOfSavedDraws;
0267
0268
0269 load([MhDirectoryName '/' M_.fname '_mh' int2str(MhFileNumber-1) '_blck' int2str(CrashedBlck) '.mat']);
0270 ilogpo2(CrashedBlck) = logpo2(end);
0271 ix2(CrashedBlck,:) = x2(end,:);
0272 NewFile(CrashedBlck) = MhFileNumber;
0273 fline(CrashedBlck,1) = 1;
0274 else
0275
0276 OpenOldFile(CrashedBlck) = 0;
0277 disp('Ok')
0278 end
0279 end
0280
0281
0282
0283 InitSizeArray = min([MAX_nruns*ones(nblck) nruns],[],2);
0284 for b = fblck:nblck
0285 if (options_.load_mh_file~=0) & (fline(b)>1) & OpenOldFile(b)
0286 load(['./' MhDirectoryName '/' M_.fname '_mh' int2str(NewFile(b)) ...
0287 '_blck' int2str(b) '.mat'])
0288 x2 = [x2;zeros(InitSizeArray(b)-fline(b)+1,npar)];
0289 logpo2 = [logpo2;zeros(InitSizeArray(b)-fline(b)+1,1)];
0290 OpenOldFile(b) = 0;
0291 else
0292 x2 = zeros(InitSizeArray(b),npar);
0293 logpo2 = zeros(InitSizeArray(b),1);
0294 end
0295 hh = waitbar(0,['Please wait... Metropolis-Hastings (' int2str(b) '/' int2str(nblck) ')...']);
0296 set(hh,'Name','Metropolis-Hastings')
0297 isux = 0;
0298 irun = fline(b);
0299 j = 1;
0300 while j <= nruns(b)
0301 par = randn(1,npar)*d;
0302 par = par.*bayestopt_.jscale' + ix2(b,:);
0303 if all(par'>mh_bounds(:,1)) & all(par'<mh_bounds(:,2))
0304 logpost = -DsgeLikelihood(par',gend,data);
0305 else
0306 logpost = -inf;
0307 end
0308 if (logpost > -inf) & (log(rand) < logpost-ilogpo2(b))
0309 x2(irun,:) = par;
0310 ix2(b,:) = par;
0311 logpo2(irun) = logpost;
0312 ilogpo2(b) = logpost;
0313 isux = isux + 1;
0314 else
0315 x2(irun,:) = ix2(b,:);
0316 logpo2(irun) = ilogpo2(b);
0317 end
0318 prtfrc = j/nruns(b);
0319 waitbar(prtfrc,hh,[ '(' int2str(b) '/' int2str(nblck) ') ' sprintf('%f done, acceptation rate %f',prtfrc,isux/j)]);
0320 if (irun == InitSizeArray(b)) | (j == nruns(b))
0321 save([MhDirectoryName '/' M_.fname '_mh' int2str(NewFile(b)) '_blck' int2str(b)],'x2','logpo2');
0322 InitSizeArray(b) = min(nruns(b)-j,MAX_nruns);
0323 if j == nruns(b)
0324 record.LastParameters(b,:) = x2(end,:);
0325 record.LastLogLiK(b) = logpo2(end);
0326 end
0327 if InitSizeArray(b)
0328 x2 = zeros(InitSizeArray(b),npar);
0329 logpo2 = zeros(InitSizeArray(b),1);
0330 NewFile(b) = NewFile(b) + 1;
0331 irun = 0;
0332 else
0333 InitSizeArray(b) = min(nruns(b),MAX_nruns);
0334 end
0335 end
0336 j=j+1;
0337 irun = irun + 1;
0338 end
0339 record.AcceptationRates(b) = isux/j;
0340 close(hh);
0341 end
0342 record.Seeds.Normal = randn('state');
0343 record.Seeds.Unifor = rand('state');
0344 save([MhDirectoryName '/' M_.fname '_mh_history'],'record');
0345 disp(['MH: Number of mh files : ' int2str(NewFile(1)) ' per block.'])
0346 disp(['MH: Total number of generated files : ' int2str(NewFile(1)*nblck) '.'])
0347 disp(['MH: Total number of iterations : ' int2str((NewFile(1)-1)*MAX_nruns+irun-1) '.'])
0348 disp(' ')