queso-0.56.0
GPMSA.C
Go to the documentation of this file.
1 //-----------------------------------------------------------------------bl-
2 //--------------------------------------------------------------------------
3 //
4 // QUESO - a library to support the Quantification of Uncertainty
5 // for Estimation, Simulation and Optimization
6 //
7 // Copyright (C) 2008-2015 The PECOS Development Team
8 //
9 // This library is free software; you can redistribute it and/or
10 // modify it under the terms of the Version 2.1 GNU Lesser General
11 // Public License as published by the Free Software Foundation.
12 //
13 // This library is distributed in the hope that it will be useful,
14 // but WITHOUT ANY WARRANTY; without even the implied warranty of
15 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 // Lesser General Public License for more details.
17 //
18 // You should have received a copy of the GNU Lesser General Public
19 // License along with this library; if not, write to the Free Software
20 // Foundation, Inc. 51 Franklin Street, Fifth Floor,
21 // Boston, MA 02110-1301 USA
22 //
23 //-----------------------------------------------------------------------el-
24 
25 #include <queso/GPMSA.h>
26 #include <queso/GslVector.h>
27 #include <queso/GslMatrix.h>
28 
29 namespace QUESO {
30 
31 template <class V, class M>
33  const VectorSet<V, M> & domain,
34  const VectorSpace<V, M> & m_scenarioSpace,
35  const VectorSpace<V, M> & m_parameterSpace,
36  const VectorSpace<V, M> & m_simulationOutputSpace,
37  const VectorSpace<V, M> & m_experimentOutputSpace,
38  const unsigned int m_numSimulations,
39  const unsigned int m_numExperiments,
40  const std::vector<V *> & m_simulationScenarios,
41  const std::vector<V *> & m_simulationParameters,
42  const std::vector<V *> & m_simulationOutputs,
43  const std::vector<V *> & m_experimentScenarios,
44  const std::vector<V *> & m_experimentOutputs,
45  const std::vector<V> & m_discrepancyBases,
46  const std::vector<M> & m_observationErrorMatrices,
47  const M & m_experimentErrors,
48  const ConcatenatedVectorRV<V, M> & m_totalPrior,
49  const V & residual_in,
50  const M & BT_Wy_B_inv_in,
51  const M & KT_K_inv_in)
52  :
53  BaseScalarFunction<V, M>("", m_totalPrior.imageSet()),
54  m_scenarioSpace(m_scenarioSpace),
55  m_parameterSpace(m_parameterSpace),
56  m_simulationOutputSpace(m_simulationOutputSpace),
57  m_experimentOutputSpace(m_experimentOutputSpace),
58  m_numSimulations(m_numSimulations),
59  m_numExperiments(m_numExperiments),
60  m_simulationScenarios(m_simulationScenarios),
61  m_simulationParameters(m_simulationParameters),
62  m_simulationOutputs(m_simulationOutputs),
63  m_experimentScenarios(m_experimentScenarios),
64  m_experimentOutputs(m_experimentOutputs),
65  m_discrepancyBases(m_discrepancyBases),
66  m_observationErrorMatrices(m_observationErrorMatrices),
67  m_experimentErrors(m_experimentErrors),
68  m_totalPrior(m_totalPrior),
69  residual(residual_in),
70  BT_Wy_B_inv(BT_Wy_B_inv_in),
71  KT_K_inv(KT_K_inv_in)
72 {
73  queso_assert_greater(m_numSimulations, 0);
74 
76  (m_simulationOutputs[0]->map().Comm().NumProc(), 1);
77 
78  const unsigned int numOutputs =
79  this->m_experimentOutputSpace.dimLocal();
80 
81  const unsigned int MAX_SVD_TERMS =
82  std::min(m_numSimulations,(unsigned int)(5));
83  num_svd_terms = std::min(MAX_SVD_TERMS, numOutputs);
84 }
85 
86 template <class V, class M>
88 {
89  // heap allocations get deleted via ScopedPtr
90 }
91 
92 template <class V, class M>
93 double
94 GPMSAEmulator<V, M>::lnValue(const V & domainVector,
95  const V * /* domainDirection */,
96  V * /* gradVector */,
97  M * /* hessianMatrix */,
98  V * /* hessianEffect */) const
99 {
100  // Components of domainVector:
101  // theta(1) // = "theta", "t" in Higdon et. al. 2008
102  // theta(2)
103  // ...
104  // theta(dimParameter)
105  // emulator_mean // = "mu"
106  // emulator_precision // = "lambda_eta"
107  // weights_precision(1) // = "lambda_{wi}" in vector case
108  // ... // nonexistent in scalar case
109  // weights_precision(num_svd_terms)
110  // emulator_corr_strength(1) // = "rho_{eta k}"
111  // ... // dimScenario = "p_x", dimParameter = "p_t"
112  // emulator_corr_strength(dimScenario + dimParameter)
113  // discrepancy_precision(1) // = "lambda_delta" in scalar case,
114  // // "lambda_{vi}" in vector
115  // ...
116  // discrepancy_precision(F) // FIXME: F = 1, |G_1| = p_delta, for now.
117  // discrepancy_corr_strength(1) // = "rho_{deltak}"
118  // ...
119  // discrepancy_corr_strength(dimScenario)
120  // emulator_data_precision(1) // = "small white noise", "small ridge"
121  // observation_error_precision // = "lambda_y", only in vector case
122 
123  // Other variables:
124  // m_numSimulations // = "m"
125  // m_numExperiments // = "n"
126  // m_simulationScenarios // = "eta"
127  // m_experimentScenarios // = "y"
128  // m_experimentErrors // = "Sigma_y"
129  // numOutputs // = "n_eta"
130  // // "n_y" := sum(n_y_i)
131  // // (== n*n_eta for us for now)
132  // dimScenario // = "p_x"
133  // num_svd_terms // = "p_eta"
134  // num_discrepancy_bases // = "p_delta"
135  // m_TruncatedSVD_simulationOutputs // = "K_eta"
136  // covMatrix // = "Sigma_D" in scalar case,
137  // "Sigma_zhat" in vector
138  // m_discrepancyMatrices // = "D_i"
139  // m_observationErrorMatrices // = "W_i"
140  // m_observationErrorMatrix // = "W_y"
141  // m_BMatrix // = "B"
142  // num_discrepancy_groups // = "F"
143  // m_emulatorPrecisionShapeVec // = "a_eta"
144  // 1.0/m_emulatorPrecisionScaleVec // = "b_eta"
145  // m_observationalPrecisionShapeVec // = "a_y"
146  // 1.0/m_observationalPrecisionScaleVec // = "b_y"
147 
148  // Construct covariance matrix
149  const unsigned int totalRuns = this->m_numExperiments + this->m_numSimulations;
150  const unsigned int numOutputs = this->m_experimentOutputSpace.dimLocal();
151  const unsigned int totalOutputs = totalRuns * numOutputs;
152  const unsigned int num_discrepancy_bases = m_discrepancyBases.size();
153  const unsigned int residualSize = (numOutputs == 1) ? totalOutputs :
154  totalRuns * num_svd_terms + m_numExperiments * num_discrepancy_bases;
155 
156  double prodScenario = 1.0;
157  double prodParameter = 1.0;
158  double prodDiscrepancy = 1.0;
159  unsigned int dimScenario = (this->m_scenarioSpace).dimLocal();
160  unsigned int dimParameter = (this->m_parameterSpace).dimLocal();
161 
162  // Length of prior+hyperprior inputs
163  unsigned int dimSum = 3 +
164  (numOutputs > 1) * 2 +
165  num_svd_terms +
166  dimParameter +
167  dimParameter +
168  dimScenario +
169  dimScenario; // yum
170 
171  // Offset for Sigma_eta equivalent in vector case
172  const unsigned int offset1 = (numOutputs == 1) ?
173  0 : m_numExperiments * num_discrepancy_bases;
174 
175  // Offset for Sigma_w in vector case
176  const unsigned int offset1b = offset1 +
177  m_numExperiments * num_svd_terms;
178 
179  // Offset for lambda_eta term in zhat covariance in vector case
180  const unsigned int offset2 = (numOutputs == 1) ?
181  0 : m_numExperiments * (num_discrepancy_bases + num_svd_terms);
182 
183  // This is cumbersome. All I want is a matrix.
184  const MpiComm & comm = domainVector.map().Comm();
185  Map z_map(residualSize, 0, comm);
186  M covMatrix(this->m_env, z_map, residualSize);
187 
188  V domainVectorParameter(*(this->m_simulationParameters[0]));
189  for (unsigned int k = 0; k < dimParameter; k++) {
190  queso_assert (!queso_isnan(domainVector[k]));
191  domainVectorParameter[k] = domainVector[k];
192  }
193 
194  // This for loop is a disaster and could do with a *lot* of optimisation
195  for (unsigned int i = 0; i < totalRuns; i++) {
196 
197  const V* scenario1;
198  const V* parameter1;
199 
200  // Decide whether to do experiment part of the covariance matrix
201  // Get i-th simulation-parameter pair
202  if (i < this->m_numExperiments) {
203  // Experiment scenario (known)
204  scenario1 = (this->m_experimentScenarios)[i];
205 
206  // Experiment parameter (unknown)
207  parameter1 = &domainVectorParameter;
208  }
209  else {
210  scenario1 =
211  (this->m_simulationScenarios)[i-this->m_numExperiments];
212  parameter1 =
213  (this->m_simulationParameters)[i-this->m_numExperiments];
214  }
215 
216  for (unsigned int j = 0; j < totalRuns; j++) {
217 
218  const V* scenario2;
219  const V* parameter2;
220 
221  if (j < this->m_numExperiments) {
222  scenario2 = (this->m_experimentScenarios)[j];
223  parameter2 = &domainVectorParameter;
224  }
225  else {
226  scenario2 =
227  (this->m_simulationScenarios)[j-this->m_numExperiments];
228  parameter2 =
229  (this->m_simulationParameters)[j-this->m_numExperiments];
230  }
231 
232  // Emulator component // = first term in (1)
233  prodScenario = 1.0;
234  unsigned int emulatorCorrStrStart =
235  dimParameter + 1 + num_svd_terms;
236  for (unsigned int k = 0; k < dimScenario; k++) {
237  const double & emulator_corr_strength =
238  domainVector[emulatorCorrStrStart+k];
239  prodScenario *= std::pow(emulator_corr_strength,
240  4.0 * ((*scenario1)[k] - (*scenario2)[k]) *
241  ((*scenario1)[k] - (*scenario2)[k]));
242  }
243 
244  queso_assert (!queso_isnan(prodScenario));
245 
246  // = second term in (1)
247  prodParameter = 1.0;
248  for (unsigned int k = 0; k < dimParameter; k++) {
249  queso_assert (!queso_isnan(domainVector[emulatorCorrStrStart+dimScenario+k]));
250  queso_assert (!queso_isnan((*parameter1)[k]));
251  queso_assert (!queso_isnan((*parameter2)[k]));
252  const double & emulator_corr_strength =
253  domainVector[emulatorCorrStrStart+dimScenario+k];
254  prodParameter *= std::pow(
255  emulator_corr_strength,
256  4.0 * ((*parameter1)[k] - (*parameter2)[k]) *
257  ((*parameter1)[k] - (*parameter2)[k]));
258  }
259 
260  queso_assert (!queso_isnan(prodParameter));
261 
262  // Sigma_eta in scalar case,
263  // [Sigma_u, Sigma_uw; Sigma_uw^T, Sigma_w] in vector case
264  for (unsigned int basis = 0; basis != num_svd_terms; ++basis)
265  {
266  // coefficient in (1)
267  // The relevant precision for Sigma_eta is lambda_eta; for
268  // Sigma_uw etc. it's lambda_wi and we skip lambda_eta
269  const double relevant_precision =
270  domainVector[dimParameter+basis+1+(numOutputs>1)];
271  queso_assert_greater(relevant_precision, 0.0);
272 
273  const unsigned int stridei =
274  (i < this->m_numExperiments) ? m_numExperiments : m_numSimulations;
275  const unsigned int offseti =
276  (i < this->m_numExperiments) ? offset1 : offset1b - m_numExperiments;
277  const unsigned int stridej =
278  (j < this->m_numExperiments) ? m_numExperiments : m_numSimulations;
279  const unsigned int offsetj =
280  (j < this->m_numExperiments) ? offset1 : offset1b - m_numExperiments;
281 
282  covMatrix(offseti+basis*stridei+i,
283  offsetj+basis*stridej+j) =
284  prodScenario * prodParameter / relevant_precision;
285  }
286 
287  // If we're in the experiment cross correlation part, need extra
288  // foo: Sigma_delta/Sigma_v and Sigma_y
289  if (i < this->m_numExperiments && j < this->m_numExperiments) {
290  V* cross_scenario1 = (this->m_simulationScenarios)[i];
291  V* cross_scenario2 = (this->m_simulationScenarios)[j];
292  prodDiscrepancy = 1.0;
293  unsigned int discrepancyCorrStrStart = dimParameter +
294  num_svd_terms +
295  dimParameter +
296  dimScenario + 2 +
297  (numOutputs > 1);
298  for (unsigned int k = 0; k < dimScenario; k++) {
299  const double & discrepancy_corr_strength =
300  domainVector[discrepancyCorrStrStart+k];
301  prodDiscrepancy *=
302  std::pow(discrepancy_corr_strength, 4.0 *
303  ((*cross_scenario1)[k] - (*cross_scenario2)[k]) *
304  ((*cross_scenario1)[k] - (*cross_scenario2)[k]));
305  }
306 
307  const double discrepancy_precision =
308  domainVector[discrepancyCorrStrStart-1];
309  queso_assert_greater(discrepancy_precision, 0);
310  queso_assert (!queso_isnan(prodDiscrepancy));
311 
312  // Sigma_delta term from below (3) in univariate case
313  // Sigma_v term from p. 576 in multivariate case
314  const double R_v = prodDiscrepancy / discrepancy_precision;
315  for (unsigned int disc = 0; disc != num_discrepancy_bases;
316  ++disc)
317  covMatrix(disc*m_numExperiments+i,
318  disc*m_numExperiments+j) += R_v;
319 
320  // Experimental error comes in via K in the multivariate
321  // case, but comes in via Sigma_y in the univariate case here
322  if (numOutputs == 1)
323  {
324  // Sigma_y term from below (3)
325  const double experimentalError =
326  (this->m_experimentErrors)(i,j);
327 
328  queso_assert_greater_equal (experimentalError, 0);
329 
330  covMatrix(i,j) += experimentalError;
331  }
332  }
333  }
334 
335  // Add small white noise component to diagonal to make stuff +ve def
336  // = "small ridge"
337  const double emulator_data_precision = domainVector[dimSum-1-(numOutputs>1)];
338  queso_assert_greater(emulator_data_precision, 0);
339  double nugget = 1.0 / emulator_data_precision;
340 
341  for (unsigned int disc = 0; disc != num_discrepancy_bases;
342  ++disc)
343  covMatrix(disc*m_numExperiments+i,
344  disc*m_numExperiments+i) += nugget;
345  }
346 
347  // If we're in the multivariate case, we've built the full Sigma_z
348  // matrix; now add the remaining Sigma_zhat terms
349  if (numOutputs > 1)
350  {
351  const double lambda_y = domainVector[dimSum-1];
352  const double inv_lambda_y = 1.0/lambda_y;
353 
354  unsigned int BT_Wy_B_size = BT_Wy_B_inv.numCols();
355  for (unsigned int i=0; i != BT_Wy_B_size; ++i)
356  for (unsigned int j=0; j != BT_Wy_B_size; ++j)
357  covMatrix(i,j) += BT_Wy_B_inv(i,j) * inv_lambda_y;
358 
359  const double emulator_precision =
360  domainVector[dimParameter+1];
361  const double inv_emulator_precision = 1.0/emulator_precision;
362 
363  unsigned int KT_K_size = KT_K_inv.numCols();
364  for (unsigned int i=0; i != KT_K_size; ++i)
365  for (unsigned int j=0; j != KT_K_size; ++j)
366  covMatrix(i+offset2,j+offset2) +=
367  KT_K_inv(i,j) * inv_emulator_precision;
368  }
369 
370 
371  // Solve covMatrix * sol = residual
372  // = Sigma_D^-1 * (D - mu 1) from (3)
373  V sol(covMatrix.invertMultiply(residual));
374 
375  // Premultiply by residual^T as in (3)
376  double minus_2_log_lhd = 0.0;
377  // There's no dot product function in GslVector.
378  for (unsigned int i = 0; i < residualSize; i++) {
379  minus_2_log_lhd += sol[i] * residual[i];
380  }
381 
382 if (queso_isnan(minus_2_log_lhd))
383  for (unsigned int i = 0; i < residualSize; i++) {
384  if (queso_isnan(sol[i]))
385  std::cout << "NaN sol[" << i << ']' << std::endl;
386  if (queso_isnan(residual[i]))
387  std::cout << "NaN residual[" << i << ']' << std::endl;
388 
389  std::cout << "Covariance Matrix:" << std::endl;
390  covMatrix.print(std::cout);
391  }
392 
393 // std::cout << "minus_2_log_lhd = " << minus_2_log_lhd << std::endl;
394 
395  queso_assert_greater(minus_2_log_lhd, 0);
396 
397  double cov_det = covMatrix.determinant();
398 
399  if (cov_det <= 0)
400  {
401  std::cout << "Non-positive determinant for covMatrix = " << std::endl;
402  covMatrix.print(std::cout);
403  queso_error();
404  }
405 
406  minus_2_log_lhd += std::log(covMatrix.determinant());
407 
408  // Multiply by -1/2 coefficient from (3)
409  return -0.5 * minus_2_log_lhd;
410 }
411 
412 template <class V, class M>
413 double
414 GPMSAEmulator<V, M>::actualValue(const V & /* domainVector */,
415  const V * /* domainDirection */,
416  V * /* gradVector */,
417  M * /* hessianMatrix */,
418  V * /* hessianEffect */) const
419 {
420  // Do nothing?
421  return 1.0;
422 }
423 
424 template <class V, class M>
426  const BaseEnvironment & env,
427  GPMSAOptions * opts,
428  const BaseVectorRV<V, M> & parameterPrior,
429  const VectorSpace<V, M> & scenarioSpace,
430  const VectorSpace<V, M> & parameterSpace,
431  const VectorSpace<V, M> & simulationOutputSpace,
432  const VectorSpace<V, M> & experimentOutputSpace,
433  unsigned int numSimulations,
434  unsigned int numExperiments)
435  :
436  m_env(env),
437  m_parameterPrior(parameterPrior),
438  m_scenarioSpace(scenarioSpace),
439  m_parameterSpace(parameterSpace),
440  m_simulationOutputSpace(simulationOutputSpace),
441  m_experimentOutputSpace(experimentOutputSpace),
442  m_numSimulations(numSimulations),
443  m_numExperiments(numExperiments),
444  m_simulationScenarios(numSimulations, (V *)NULL),
445  m_simulationParameters(numSimulations, (V *)NULL),
446  m_simulationOutputs(numSimulations, (V *)NULL),
447  m_experimentScenarios(numExperiments, (V *)NULL),
448  m_experimentOutputs(numExperiments, (V *)NULL),
449  m_numSimulationAdds(0),
450  m_numExperimentAdds(0),
451  priors(7, (const BaseVectorRV<V, M> *)NULL), // Needed for gcc 4.3.2
452  m_constructedGP(false)
453 {
454  // We should have the same number of outputs from both simulations
455  // and experiments
456  queso_assert_equal_to(simulationOutputSpace.dimGlobal(),
457  experimentOutputSpace.dimGlobal());
458 
459  {
460  const unsigned int numOutputs =
461  this->m_experimentOutputSpace.dimLocal();
462  const Map & output_map = experimentOutputSpace.map();
463 
464  // Set up the default discrepancy basis:
465  V all_ones_basis(env, output_map);
466  for (unsigned int i=0; i != numOutputs; ++i)
467  all_ones_basis[i] = 1;
468  m_discrepancyBases.push_back(all_ones_basis);
469 
470  // Set up the default observation error covariance matrix:
471 
472  M identity_matrix(env, output_map, 1.0);
473 
474  for (unsigned int i = 0; i != numExperiments; ++i)
475  m_observationErrorMatrices.push_back(identity_matrix);
476  }
477 
478  // DM: Not sure if the logic in these 3 if-blocks is correct
479  if ((opts == NULL) && (this->m_env.optionsInputFileName() == "")) {
480  queso_error_msg("Must options object or an input file");
481  }
482 
483  if (opts != NULL) {
484  allocated_m_opts = false;
485  this->m_opts = opts;
486  }
487  else {
488  // Create a default one
489  allocated_m_opts = true;
490  this->m_opts = new GPMSAOptions(this->m_env, "");
491  }
492 
493  // FIXME: WTF? - RHS
494  // this->m_constructedGP = false;
495 }
496 
497 template <class V, class M>
499 {
500  if (this->allocated_m_opts)
501  delete this->m_opts;
502 }
503 
504 template <class V, class M>
505 unsigned int
507 {
508  return this->m_numSimulations;
509 }
510 
511 template <class V, class M>
512 unsigned int
514 {
515  return this->m_numExperiments;
516 }
517 
518 template <class V, class M>
519 const VectorSpace<V, M> &
521 {
522  return this->m_scenarioSpace;
523 }
524 
525 template <class V, class M>
526 const VectorSpace<V, M> &
528 {
529  return this->m_parameterSpace;
530 }
531 
532 template <class V, class M>
533 const VectorSpace<V, M> &
535 {
536  return this->m_simulationOutputSpace;
537 }
538 
539 template <class V, class M>
540 const VectorSpace<V, M> &
542 {
543  return this->m_experimentOutputSpace;
544 }
545 
546 template <class V, class M>
547 const V &
549  unsigned int simulationId) const
550 {
551  queso_require_less_msg(simulationId, m_simulationScenarios.size(), "simulationId is too large");
552 
553  queso_require_msg(m_simulationScenarios[simulationId], "vector is NULL");
554 
555  return *(this->m_simulationScenarios[simulationId]);
556 }
557 
558 template <class V, class M>
559 const std::vector<V *> &
561 {
562  return this->m_simulationScenarios;
563 }
564 
565 template <class V, class M>
566 const V &
568  unsigned int simulationId) const
569 {
570  queso_require_less_msg(simulationId, m_simulationParameters.size(), "simulationId is too large");
571 
572  queso_require_msg(m_simulationParameters[simulationId], "vector is NULL");
573 
574  return *(this->m_simulationParameters[simulationId]);
575 }
576 
577 template <class V, class M>
578 const std::vector<V *> &
580 {
581  return this->m_simulationParameters;
582 }
583 
584 template <class V, class M>
585 const V &
587  unsigned int simulationId) const
588 {
589  queso_require_less_msg(simulationId, m_simulationOutputs.size(), "simulationId is too large");
590 
591  queso_require_msg(m_simulationOutputs[simulationId], "vector is NULL");
592 
593  return *(this->m_simulationOutputs[simulationId]);
594 }
595 
596 template <class V, class M>
597 const std::vector<V *> &
599 {
600  return this->m_simulationOutputs;
601 }
602 
603 template <class V, class M>
604 const V &
606  unsigned int experimentId) const
607 {
608  queso_require_less_msg(experimentId, (this->m_experimentScenarios).size(), "experimentId is too large");
609 
610  queso_require_msg(this->m_experimentScenarios[experimentId], "vector is NULL");
611 
612  return *(this->m_experimentScenarios[experimentId]);
613 }
614 
615 template <class V, class M>
616 const std::vector<V *> &
618 {
619  return this->m_experimentScenarios;
620 }
621 
622 template <class V, class M>
623 const V &
625  unsigned int experimentId) const
626 {
627  queso_require_less_msg(experimentId, (this->m_experimentOutputs).size(), "experimentId is too large");
628 
629  queso_require_msg(this->m_experimentOutputs[experimentId], "vector is NULL");
630 
631  return *(this->m_experimentOutputs[experimentId]);
632 }
633 
634 template <class V, class M>
635 const std::vector<V *> &
637 {
638  return this->m_experimentOutputs;
639 }
640 
641 template <class V, class M>
642 const M &
644 {
645  return *(this->m_experimentErrors);
646 }
647 
648 template <class V, class M>
649 const BaseEnvironment &
651 {
652  return this->m_env;
653 }
654 
655 template <class V, class M>
656 const GPMSAEmulator<V, M> &
658 {
659  return *(this->gpmsaEmulator);
660 }
661 
662 template <class V, class M>
663 void
664 GPMSAFactory<V, M>::addSimulation(V & simulationScenario,
665  V & simulationParameter,
666  V & simulationOutput)
667 {
668  queso_require_less_msg(this->m_numSimulationAdds, this->m_numSimulations, "too many simulation adds...");
669 
670  this->m_simulationScenarios[this->m_numSimulationAdds] = &simulationScenario;
671  this->m_simulationParameters[this->m_numSimulationAdds] = &simulationParameter;
672  this->m_simulationOutputs[this->m_numSimulationAdds] = &simulationOutput;
673  this->m_numSimulationAdds++;
674 
675  if ((this->m_numSimulationAdds == this->m_numSimulations) &&
676  (this->m_numExperimentAdds == this->m_numExperiments) &&
677  (this->m_constructedGP == false)) {
678  this->setUpEmulator();
679  }
680 }
681 
682 template <class V, class M>
683 void
685  const std::vector<V *> & simulationScenarios,
686  const std::vector<V *> & simulationParameters,
687  const std::vector<V *> & simulationOutputs)
688 {
689  for (unsigned int i = 0; i < this->m_numSimulations; i++) {
690  this->addSimulation(*(simulationScenarios[i]), *(simulationParameters[i]),
691  *(simulationOutputs[i]));
692  }
693 }
694 
695 
696 
697 template <class V, class M>
698 void
700 {
701  const unsigned int numOutputs =
702  this->m_experimentOutputSpace.dimLocal();
703  const unsigned int MAX_SVD_TERMS =
704  std::min(m_numSimulations,(unsigned int)(5));
705  const unsigned int num_svd_terms =
706  std::min(MAX_SVD_TERMS, numOutputs);
707 
708  const Map & output_map = m_simulationOutputs[0]->map();
709 
710  const MpiComm & comm = output_map.Comm();
711 
712  Map serial_map(m_numSimulations, 0, comm);
713 
714  const BaseEnvironment &env = m_simulationOutputs[0]->env();
715 
716  simulationOutputMeans.reset
717  (new V (env, output_map));
718 
719  for (unsigned int i=0; i != m_numSimulations; ++i)
720  for (unsigned int j=0; j != numOutputs; ++j)
721  (*simulationOutputMeans)[j] += (*m_simulationOutputs[i])[j];
722 
723  for (unsigned int j=0; j != numOutputs; ++j)
724  (*simulationOutputMeans)[j] /= m_numSimulations;
725 
726  M simulation_matrix(env, serial_map, numOutputs);
727 
728  for (unsigned int i=0; i != m_numSimulations; ++i)
729  for (unsigned int j=0; j != numOutputs; ++j)
730  simulation_matrix(i,j) =
731  (*m_simulationOutputs[i])[j] - (*simulationOutputMeans)[j];
732 
733  // GSL only finds left singular vectors if n_rows>=n_columns, so we need to
734  // calculate them indirectly from the eigenvalues of M^T*M
735 
736  M S_trans(simulation_matrix.transpose());
737 
738  M SM_squared(S_trans*simulation_matrix);
739 
740  M SM_singularVectors(env, SM_squared.map(), numOutputs);
741  V SM_singularValues(env, SM_squared.map());
742 
743  SM_squared.eigen(SM_singularValues, &SM_singularVectors);
744 
745  // Copy only those vectors we want into K_eta
746  m_TruncatedSVD_simulationOutputs.reset
747  (new M(env, output_map, num_svd_terms));
748 
749  for (unsigned int i=0; i != numOutputs; ++i)
750  for (unsigned int k = 0; k != num_svd_terms; ++k)
751  (*m_TruncatedSVD_simulationOutputs)(i,k) = SM_singularVectors(i,k);
752 
753  Map copied_map(numOutputs * m_numSimulations, 0, comm);
754 
755  K.reset
756  (new M(env, copied_map, m_numSimulations * num_svd_terms));
757  for (unsigned int k=0; k != num_svd_terms; ++k)
758  for (unsigned int i1=0; i1 != m_numSimulations; ++i1)
759  for (unsigned int i2=0; i2 != numOutputs; ++i2)
760  {
761  const unsigned int i = i1 * numOutputs + i2;
762  const unsigned int j = k * m_numSimulations + i1;
763  (*K)(i,j) = SM_singularVectors(i2,k);
764  }
765 
766  KT_K_inv.reset
767  (new M((K->transpose() * *K).inverse()));
768 
769  Map serial_output_map(numOutputs, 0, comm);
770 
771  for (unsigned int i = 0; i != m_numExperiments; ++i)
772  {
773  M D_i(env, serial_output_map,
774  (unsigned int)(m_discrepancyBases.size()));
775 
776  for (unsigned int j=0; j != numOutputs; ++j)
777  for (unsigned int k=0; k != m_discrepancyBases.size(); ++k)
778  D_i(j,k) = m_discrepancyBases[k][j];
779 
780  m_discrepancyMatrices.push_back(D_i);
781  }
782 
783  // Create the giant matrices!
784 
785  // We build B from two parts, the diag(D_i)*P_D^T block and
786  // the diag(K_i)*P_K^T block, but we build simultaneously so we only
787  // need one loop over experiments.
788  // Since P_D and P_K are permutation matrices we'll just apply the
789  // permutations as we insert.
790 
791  // W_y is simple block diagonal.
792 
793  // Neither of these ought to be dense matrices but we're sacrificing
794  // efficiency for clarity for now.
795 
796  const unsigned int num_discrepancy_bases = m_discrepancyBases.size();
797  const unsigned int Brows = m_numExperiments * numOutputs;
798  const unsigned int Bcols =
799  m_numExperiments * (num_discrepancy_bases + num_svd_terms);
800 
801  const Map B_row_map(Brows, 0, comm);
802 
803  m_BMatrix.reset
804  (new M(env, B_row_map, Bcols));
805 
806  const unsigned int Wyrows = m_numExperiments * numOutputs;
807 
808  const Map Wy_row_map(Wyrows, 0, comm);
809 
810  m_observationErrorMatrix.reset
811  (new M(env, Wy_row_map, Wyrows));
812 
813  M& B = *m_BMatrix;
814  M& Wy = *m_observationErrorMatrix;
815 
816  for (unsigned int ex = 0; ex != m_numExperiments; ++ex)
817  {
818  const M & D_i = m_discrepancyMatrices[ex];
819 
820  // For the multivariate case, the bases K_eta computed from
821  // simulator outputs are the same as the bases K_i which apply
822  // to quantities of interest, because simulator outputs are QoIs
823  // alone.
824  //
825  // FIXME - we need to interpolate K_i in the functional case.
826 
827  for (unsigned int outi = 0; outi != numOutputs; ++outi)
828  {
829  unsigned int i = ex*numOutputs+outi;
830  for (unsigned int outj = 0; outj != num_discrepancy_bases; ++outj)
831  {
832  unsigned int j = ex + m_numExperiments * outj;
833 
834  B(i,j) = D_i(outi,outj);
835  }
836 
837  for (unsigned int outj = 0; outj != num_svd_terms; ++outj)
838  {
839  unsigned int j = ex +
840  m_numExperiments * (num_discrepancy_bases + outj);
841 
842  B(i,j) = (*m_TruncatedSVD_simulationOutputs)(outi,outj);
843  }
844 
845  for (unsigned int outj = 0; outj != numOutputs; ++outj)
846  {
847  // No fancy perturbation here
848  unsigned int j = ex*numOutputs+outj;
849 
850  Wy(i,j) = m_observationErrorMatrices[ex](outi,outj);
851  }
852  }
853  }
854 
855  M BT_Wy_B (B.transpose() * Wy * B);
856 
857  // Adding a "small ridge" to make sure this is invertible, as on
858  // p.577 - using 1e-4 from discussion notes.
859  for (unsigned int i=0; i != Brows; ++i)
860  BT_Wy_B(i,i) += 1.e-4;
861 
862  BT_Wy_B_inv.reset(new M(BT_Wy_B.inverse()));
863 
864  this->setUpHyperpriors();
865 
866  this->m_constructedGP = true;
867  this->gpmsaEmulator.reset
868  (new GPMSAEmulator<V, M>(
869  this->prior().imageSet(),
870  this->m_scenarioSpace,
871  this->m_parameterSpace,
872  this->m_simulationOutputSpace,
873  this->m_experimentOutputSpace,
874  this->m_numSimulations,
875  this->m_numExperiments,
876  this->m_simulationScenarios,
877  this->m_simulationParameters,
878  this->m_simulationOutputs,
879  this->m_experimentScenarios,
880  this->m_experimentOutputs,
881  this->m_discrepancyBases,
882  this->m_observationErrorMatrices,
883  *(this->m_experimentErrors),
884  *(this->m_totalPrior),
885  *this->residual,
886  *this->BT_Wy_B_inv,
887  *this->KT_K_inv));
888 }
889 
890 
891 
892 template <class V, class M>
893 void
895  const std::vector<V *> & experimentScenarios,
896  const std::vector<V *> & experimentOutputs,
897  const M * experimentErrors)
898 {
899  queso_require_less_equal_msg(experimentScenarios.size(), this->m_numExperiments, "too many experiments...");
900 
901  for (unsigned int i = 0; i < this->m_experimentScenarios.size(); i++) {
902  this->m_experimentScenarios[i] = experimentScenarios[i];
903  this->m_experimentOutputs[i] = experimentOutputs[i];
904  }
905  this->m_experimentErrors = experimentErrors;
906  this->m_numExperimentAdds += experimentScenarios.size();
907 
908  if ((this->m_numSimulationAdds == this->m_numSimulations) &&
909  (this->m_numExperimentAdds == this->m_numExperiments) &&
910  (this->m_constructedGP == false)) {
911  this->setUpEmulator();
912  }
913 }
914 
915 
916 template <class V, class M>
917 void
919  const std::vector<V *> & discrepancyBases)
920 {
921  m_discrepancyBases.clear();
922 
923  for (unsigned int i = 0; i < discrepancyBases.size(); i++) {
924  m_discrepancyBases.push_back(*(discrepancyBases[i]));
925  }
926 
927  // We should not yet have constructed the underlying GP model
928  queso_assert_equal_to(this->m_constructedGP, false);
929 }
930 
931 
932 
933 template <class V, class M>
934 M &
936  (unsigned int simulationNumber)
937 {
938  queso_assert_less(simulationNumber, m_numSimulations);
939  queso_assert_equal_to(m_observationErrorMatrices.size(), m_numSimulations);
940 
941  return m_observationErrorMatrices[simulationNumber];
942 }
943 
944 
945 template <class V, class M>
946 const M &
948  (unsigned int simulationNumber) const
949 {
950  queso_assert_less(simulationNumber, m_numSimulations);
951  queso_assert_equal_to(m_observationErrorMatrices.size(), m_numSimulations);
952 
953  return m_observationErrorMatrices[simulationNumber];
954 }
955 
956 
957 
958 template <class V, class M>
961 {
962  return *(this->m_totalPrior);
963 }
964 
965 template <class V, class M>
966 void
967 GPMSAFactory<V, M>::print(std::ostream& /* os */) const
968 {
969  // Do nothing
970 }
971 
972 // Private methods follow
973 template <class V, class M>
974 void
976 {
977  const unsigned int numOutputs =
978  this->m_experimentOutputSpace.dimLocal();
979  const unsigned int MAX_SVD_TERMS =
980  std::min(m_numSimulations,(unsigned int)(5));
981  const unsigned int num_svd_terms =
982  std::min(MAX_SVD_TERMS, numOutputs);
983  const unsigned int num_discrepancy_bases = m_discrepancyBases.size();
984 
985  const MpiComm & comm = m_simulationOutputs[0]->map().Comm();
986 
987  unsigned int rank_B;
988  if (m_BMatrix->numRowsGlobal() > m_BMatrix->numCols())
989  rank_B = m_BMatrix->rank(0, 1.e-4);
990  else
991  rank_B = m_BMatrix->transpose().rank(0, 1.e-4);
992 
993  double emulatorPrecisionShape = this->m_opts->m_emulatorPrecisionShape;
994  double emulatorPrecisionScale = this->m_opts->m_emulatorPrecisionScale;
995 
996  double observationalPrecisionShape = this->m_opts->m_observationalPrecisionShape;
997  double observationalPrecisionScale = this->m_opts->m_observationalPrecisionScale;
998 
999  if (numOutputs > 1)
1000  {
1001  Map y_map(m_numExperiments * numOutputs, 0, comm);
1002  Map eta_map(m_numSimulations * numOutputs, 0, comm);
1003 
1004  const unsigned int yhat_size =
1005  m_numExperiments * (num_discrepancy_bases + num_svd_terms);
1006 
1007  const unsigned int etahat_size =
1008  m_numSimulations * num_svd_terms;
1009 
1010  Map zhat_map(yhat_size + etahat_size, 0, comm);
1011 
1012  V y(this->m_env, y_map);
1013  V eta(this->m_env, eta_map);
1014 
1015  for (unsigned int i = 0; i < this->m_numExperiments; i++) {
1016  for (unsigned int k = 0; k != numOutputs; ++k)
1017  y[i*numOutputs+k] =
1018  (*((this->m_experimentOutputs)[i]))[k] -
1019  (*simulationOutputMeans)[k];
1020  }
1021 
1022  for (unsigned int i = 0; i < this->m_numSimulations; i++) {
1023  for (unsigned int k = 0; k != numOutputs; ++k)
1024  eta[i*numOutputs+k] =
1025  (*((this->m_simulationOutputs)[i]))[k] -
1026  (*simulationOutputMeans)[k];
1027  }
1028 
1029  M& B = *m_BMatrix;
1030  M& Wy = *m_observationErrorMatrix;
1031 
1032  V yhat(*BT_Wy_B_inv * (B.transpose() * (Wy * y)));
1033 
1034  queso_assert_equal_to(yhat.sizeGlobal(), yhat_size);
1035 
1036  V etahat(*KT_K_inv * (K->transpose() * eta));
1037 
1038  residual.reset(new V(this->m_env, zhat_map));
1039  for (unsigned int i = 0; i < yhat_size; ++i)
1040  (*residual)[i] = yhat[i];
1041 
1042  for (unsigned int i = 0; i < etahat_size; ++i)
1043  (*residual)[yhat_size+i] = etahat[i];
1044 
1045  emulatorPrecisionShape +=
1046  (this->m_numSimulations * (numOutputs - num_svd_terms)) / 2.0;
1047 
1048  V eta_temp(eta);
1049  eta_temp -= *K * etahat;
1050 
1051  emulatorPrecisionScale +=
1052  scalarProduct(eta, eta_temp) / 2.0;
1053 
1054  observationalPrecisionShape +=
1055  (this->m_numExperiments * numOutputs - rank_B) / 2.0;
1056 
1057  V y_temp(Wy * y);
1058  y_temp -= Wy * B * yhat;
1059 
1060  observationalPrecisionScale +=
1061  scalarProduct(y, y_temp) / 2.0;
1062  }
1063  else
1064  {
1065  const unsigned int totalRuns = this->m_numExperiments + this->m_numSimulations;
1066  Map z_map(totalRuns, 0, comm);
1067  residual.reset(new V (this->m_env, z_map));
1068 
1069  // Form residual = D - mean // = D - mu*1 in (3)
1070  // We currently use the mean of the simulation data, not a free
1071  // hyperparameter mean
1072  for (unsigned int i = 0; i < this->m_numExperiments; i++) {
1073  (*residual)[i] = (*((this->m_experimentOutputs)[i]))[0] -
1074  (*simulationOutputMeans)[0];
1075  }
1076  for (unsigned int i = 0; i < this->m_numSimulations; i++) {
1077  (*residual)[i+this->m_numExperiments] =
1078  (*((this->m_simulationOutputs)[i]))[0] -
1079  (*simulationOutputMeans)[0];
1080  }
1081  }
1082 
1083 
1084  double emulatorCorrelationStrengthAlpha = this->m_opts->m_emulatorCorrelationStrengthAlpha;
1085  double emulatorCorrelationStrengthBeta = this->m_opts->m_emulatorCorrelationStrengthBeta;
1086  double discrepancyPrecisionShape = this->m_opts->m_discrepancyPrecisionShape;
1087  double discrepancyPrecisionScale = this->m_opts->m_discrepancyPrecisionScale;
1088  double discrepancyCorrelationStrengthAlpha = this->m_opts->m_discrepancyCorrelationStrengthAlpha;
1089  double discrepancyCorrelationStrengthBeta = this->m_opts->m_discrepancyCorrelationStrengthBeta;
1090  double emulatorDataPrecisionShape = this->m_opts->m_emulatorDataPrecisionShape;
1091  double emulatorDataPrecisionScale = this->m_opts->m_emulatorDataPrecisionScale;
1092 
1093  this->oneDSpace.reset
1094  (new VectorSpace<V, M>(this->m_env, "", 1, NULL));
1095 
1096  // Emulator mean
1097  this->emulatorMeanMin.reset(new V(this->oneDSpace->zeroVector()));
1098  this->emulatorMeanMax.reset(new V(this->oneDSpace->zeroVector()));
1099  this->emulatorMeanMin->cwSet(-INFINITY);
1100  this->emulatorMeanMax->cwSet(INFINITY);
1101 
1102  this->emulatorMeanDomain.reset
1103  (new BoxSubset<V, M>
1104  ("",
1105  *(this->oneDSpace),
1106  *(this->emulatorMeanMin),
1107  *(this->emulatorMeanMax)));
1108 
1109  this->m_emulatorMean.reset
1111  ("",
1112  *(this->emulatorMeanDomain)));
1113 
1114  // Emulator precision
1115  this->emulatorPrecisionSpace.reset
1116  (new VectorSpace<V, M>
1117  (this->m_env,
1118  "",
1119  num_svd_terms + (numOutputs > 1),
1120  NULL));
1121 
1122  this->emulatorPrecisionMin.reset
1123  (new V(this->emulatorPrecisionSpace->zeroVector()));
1124  this->emulatorPrecisionMax.reset
1125  (new V(this->emulatorPrecisionSpace->zeroVector()));
1126  this->m_emulatorPrecisionShapeVec.reset
1127  (new V(this->emulatorPrecisionSpace->zeroVector()));
1128  this->m_emulatorPrecisionScaleVec.reset
1129  (new V(this->emulatorPrecisionSpace->zeroVector()));
1130  this->emulatorPrecisionMin->cwSet(0.3);
1131  this->emulatorPrecisionMax->cwSet(INFINITY);
1132  this->m_emulatorPrecisionShapeVec->cwSet(emulatorPrecisionShape);
1133  this->m_emulatorPrecisionScaleVec->cwSet(emulatorPrecisionScale);
1134 
1135  this->emulatorPrecisionDomain.reset
1136  (new BoxSubset<V, M>
1137  ("",
1138  *(this->emulatorPrecisionSpace),
1139  *(this->emulatorPrecisionMin),
1140  *(this->emulatorPrecisionMax)));
1141 
1142  this->m_emulatorPrecision.reset
1143  (new GammaVectorRV<V, M>
1144  ("",
1145  *(this->emulatorPrecisionDomain),
1146  *(this->m_emulatorPrecisionShapeVec),
1147  *(this->m_emulatorPrecisionScaleVec)));
1148 
1149  // Emulator correlation strength
1150  unsigned int dimScenario = (this->scenarioSpace()).dimLocal();
1151  unsigned int dimParameter = (this->parameterSpace()).dimLocal();
1152  this->emulatorCorrelationSpace.reset
1153  (new VectorSpace<V, M>
1154  (this->m_env,
1155  "",
1156  dimScenario + dimParameter,
1157  NULL));
1158 
1159  this->emulatorCorrelationMin.reset
1160  (new V(this->emulatorCorrelationSpace->zeroVector()));
1161  this->emulatorCorrelationMax.reset
1162  (new V(this->emulatorCorrelationSpace->zeroVector()));
1163  this->m_emulatorCorrelationStrengthAlphaVec.reset
1164  (new V(this->emulatorCorrelationSpace->zeroVector()));
1165  this->m_emulatorCorrelationStrengthBetaVec.reset
1166  (new V(this->emulatorCorrelationSpace->zeroVector()));
1167  this->emulatorCorrelationMin->cwSet(0);
1168  this->emulatorCorrelationMax->cwSet(1);
1169  this->m_emulatorCorrelationStrengthAlphaVec->cwSet(emulatorCorrelationStrengthAlpha);
1170  this->m_emulatorCorrelationStrengthBetaVec->cwSet(emulatorCorrelationStrengthBeta);
1171 
1172  this->emulatorCorrelationDomain.reset
1173  (new BoxSubset<V, M>
1174  ("",
1175  *(this->emulatorCorrelationSpace),
1176  *(this->emulatorCorrelationMin),
1177  *(this->emulatorCorrelationMax)));
1178 
1179  this->m_emulatorCorrelationStrength.reset
1180  (new BetaVectorRV<V, M>
1181  ("",
1182  *(this->emulatorCorrelationDomain),
1183  *(this->m_emulatorCorrelationStrengthAlphaVec),
1184  *(this->m_emulatorCorrelationStrengthBetaVec)));
1185 
1186  // Observation precision
1187  this->observationalPrecisionSpace.reset
1188  (new VectorSpace<V, M>
1189  (this->m_env,
1190  "",
1191  1,
1192  NULL));
1193 
1194  this->observationalPrecisionMin.reset
1195  (new V(this->observationalPrecisionSpace->zeroVector()));
1196  this->observationalPrecisionMax.reset
1197  (new V(this->observationalPrecisionSpace->zeroVector()));
1198  this->m_observationalPrecisionShapeVec.reset
1199  (new V(this->observationalPrecisionSpace->zeroVector()));
1200  this->m_observationalPrecisionScaleVec.reset
1201  (new V(this->observationalPrecisionSpace->zeroVector()));
1202  this->observationalPrecisionMin->cwSet(0.3);
1203  this->observationalPrecisionMax->cwSet(INFINITY);
1204  this->m_observationalPrecisionShapeVec->cwSet
1205  (this->m_opts->m_observationalPrecisionShape);
1206  this->m_observationalPrecisionScaleVec->cwSet
1207  (this->m_opts->m_observationalPrecisionScale);
1208 
1209  this->observationalPrecisionDomain.reset
1210  (new BoxSubset<V, M>
1211  ("",
1212  *(this->observationalPrecisionSpace),
1213  *(this->observationalPrecisionMin),
1214  *(this->observationalPrecisionMax)));
1215 
1216  this->m_observationalPrecision.reset
1217  (new GammaVectorRV<V, M>
1218  ("",
1219  *(this->observationalPrecisionDomain),
1220  *(this->m_observationalPrecisionShapeVec),
1221  *(this->m_observationalPrecisionScaleVec)));
1222 
1223  // Discrepancy precision
1224  this->discrepancyPrecisionMin.reset
1225  (new V(this->oneDSpace->zeroVector()));
1226  this->discrepancyPrecisionMax.reset
1227  (new V(this->oneDSpace->zeroVector()));
1228  this->m_discrepancyPrecisionShapeVec.reset
1229  (new V(this->oneDSpace->zeroVector()));
1230  this->m_discrepancyPrecisionScaleVec.reset
1231  (new V(this->oneDSpace->zeroVector()));
1232  this->discrepancyPrecisionMin->cwSet(0);
1233  this->discrepancyPrecisionMax->cwSet(INFINITY);
1234  this->m_discrepancyPrecisionShapeVec->cwSet(discrepancyPrecisionShape);
1235  this->m_discrepancyPrecisionScaleVec->cwSet(discrepancyPrecisionScale);
1236 
1237  this->discrepancyPrecisionDomain.reset
1238  (new BoxSubset<V, M>
1239  ("",
1240  *(this->oneDSpace),
1241  *(this->discrepancyPrecisionMin),
1242  *(this->discrepancyPrecisionMax)));
1243 
1244  this->m_discrepancyPrecision.reset
1245  (new GammaVectorRV<V, M>
1246  ("",
1247  *(this->discrepancyPrecisionDomain),
1248  *(this->m_discrepancyPrecisionShapeVec),
1249  *(this->m_discrepancyPrecisionScaleVec)));
1250 
1251  // Discrepancy correlation strength
1252  this->discrepancyCorrelationSpace.reset
1253  (new VectorSpace<V, M>
1254  (this->m_env,
1255  "",
1256  dimScenario,
1257  NULL));
1258 
1259  this->discrepancyCorrelationMin.reset
1260  (new V(this->discrepancyCorrelationSpace->zeroVector()));
1261  this->discrepancyCorrelationMax.reset
1262  (new V(this->discrepancyCorrelationSpace->zeroVector()));
1263  this->m_discrepancyCorrelationStrengthAlphaVec.reset
1264  (new V(this->discrepancyCorrelationSpace->zeroVector()));
1265  this->m_discrepancyCorrelationStrengthBetaVec.reset
1266  (new V(this->discrepancyCorrelationSpace->zeroVector()));
1267  this->discrepancyCorrelationMin->cwSet(0);
1268  this->discrepancyCorrelationMax->cwSet(1);
1269  this->m_discrepancyCorrelationStrengthAlphaVec->cwSet(discrepancyCorrelationStrengthAlpha);
1270  this->m_discrepancyCorrelationStrengthBetaVec->cwSet(discrepancyCorrelationStrengthBeta);
1271 
1272  this->discrepancyCorrelationDomain.reset
1273  (new BoxSubset<V, M>
1274  ("",
1275  *(this->discrepancyCorrelationSpace),
1276  *(this->discrepancyCorrelationMin),
1277  *(this->discrepancyCorrelationMax)));
1278 
1279  this->m_discrepancyCorrelationStrength.reset
1280  (new BetaVectorRV<V, M>
1281  ("",
1282  *(this->discrepancyCorrelationDomain),
1283  *(this->m_discrepancyCorrelationStrengthAlphaVec),
1284  *(this->m_discrepancyCorrelationStrengthBetaVec)));
1285 
1286  // Emulator data precision
1287  this->emulatorDataPrecisionMin.reset
1288  (new V(this->oneDSpace->zeroVector()));
1289  this->emulatorDataPrecisionMax.reset
1290  (new V(this->oneDSpace->zeroVector()));
1291  this->m_emulatorDataPrecisionShapeVec.reset
1292  (new V(this->oneDSpace->zeroVector()));
1293  this->m_emulatorDataPrecisionScaleVec.reset
1294  (new V(this->oneDSpace->zeroVector()));
1295  this->emulatorDataPrecisionMin->cwSet(60.0);
1296  this->emulatorDataPrecisionMax->cwSet(1e5);
1297  this->m_emulatorDataPrecisionShapeVec->cwSet(emulatorDataPrecisionShape);
1298  this->m_emulatorDataPrecisionScaleVec->cwSet(emulatorDataPrecisionScale);
1299 
1300  this->emulatorDataPrecisionDomain.reset
1301  (new BoxSubset<V, M>
1302  ("",
1303  *(this->oneDSpace),
1304  *(this->emulatorDataPrecisionMin),
1305  *(this->emulatorDataPrecisionMax)));
1306 
1307  this->m_emulatorDataPrecision.reset
1308  (new GammaVectorRV<V, M>
1309  ("",
1310  *(this->emulatorDataPrecisionDomain),
1311  *(this->m_emulatorDataPrecisionShapeVec),
1312  *(this->m_emulatorDataPrecisionScaleVec)));
1313 
1314  // Now form full prior
1315  unsigned int dimSum = 3 +
1316  (numOutputs > 1) * 2 +
1317  num_svd_terms +
1318  dimParameter +
1319  dimParameter +
1320  dimScenario +
1321  dimScenario; // yum
1322 
1323  this->totalSpace.reset
1324  (new VectorSpace<V, M>
1325  (this->m_env,
1326  "",
1327  dimSum,
1328  NULL));
1329  this->totalMins.reset(new V(this->totalSpace->zeroVector()));
1330  this->totalMaxs.reset(new V(this->totalSpace->zeroVector()));
1331 
1332  // Hackety hack McHackington. There's no better way to do this unfortunately
1333  this->totalMins->cwSet(0);
1334  this->totalMaxs->cwSet(1);
1335 
1336  (*(this->totalMins))[dimParameter] = -INFINITY; // Min mean
1337  (*(this->totalMaxs))[dimParameter] = INFINITY; // Max mean
1338 
1339  // Min emulator precision
1340  (*(this->totalMins))[dimParameter+1] = 0.3;
1341  // Max emulator precision
1342  (*(this->totalMaxs))[dimParameter+1] = INFINITY;
1343 
1344  if (numOutputs > 1)
1345  for (unsigned int basis = 0; basis != num_svd_terms; ++basis)
1346  {
1347  // Min weights precision
1348  (*(this->totalMins))[dimParameter+2+basis] = 0.3;
1349  // Max weights precision
1350  (*(this->totalMaxs))[dimParameter+2+basis] = INFINITY;
1351  }
1352 
1353  // FIXME: F = 1 for now
1354  // Min discrepancy precision
1355  (*(this->totalMins))[dimParameter+1+(numOutputs>1)+num_svd_terms+dimScenario+dimParameter] = 0;
1356  // Max discrepancy precision
1357  (*(this->totalMaxs))[dimParameter+1+(numOutputs>1)+num_svd_terms+dimScenario+dimParameter] = INFINITY;
1358 
1359  (*(this->totalMins))[dimSum-1-(numOutputs>1)] = 60.0; // Min emulator data precision
1360  (*(this->totalMaxs))[dimSum-1-(numOutputs>1)] = 1e5; // Max emulator data precision
1361 
1362  if (numOutputs>1) {
1363  (*(this->totalMins))[dimSum-1] = 0.3; // Min observation error precision
1364  (*(this->totalMaxs))[dimSum-1] = INFINITY; // Max observation error precision
1365  }
1366 
1367  this->totalDomain.reset
1368  (new BoxSubset<V, M>
1369  ("",
1370  *(this->totalSpace),
1371  *(this->totalMins),
1372  *(this->totalMaxs)));
1373 
1374  this->priors[0] = &(this->m_parameterPrior);
1375  this->priors[1] = this->m_emulatorMean.get();
1376  this->priors[2] = this->m_emulatorPrecision.get();
1377  this->priors[3] = this->m_emulatorCorrelationStrength.get();
1378  this->priors[4] = this->m_discrepancyPrecision.get();
1379  this->priors[5] = this->m_discrepancyCorrelationStrength.get();
1380  this->priors[6] = this->m_emulatorDataPrecision.get();
1381  if (numOutputs > 1)
1382  this->priors.push_back(this->m_observationalPrecision.get());
1383 
1384  // Finally
1385  this->m_totalPrior.reset
1387  ("",
1388  this->priors,
1389  *(this->totalDomain)));
1390 }
1391 
1392 } // End namespace QUESO
1393 
void print(std::ostream &os) const
Definition: GPMSA.C:967
const Map & map() const
Map.
Definition: VectorSpace.C:157
RawType_MPI_Comm Comm() const
Extract MPI Communicator from a MpiComm object.
Definition: MpiComm.C:105
M & getObservationErrorCovariance(unsigned int simulationNumber)
Definition: GPMSA.C:936
A templated (base) class for handling scalar functions.
std::vector< V > m_discrepancyBases
Definition: GPMSA.h:328
const ConcatenatedVectorRV< V, M > & prior() const
Definition: GPMSA.C:960
A class representing a vector RV constructed via Beta distribution.
Definition: BetaVectorRV.h:63
std::string optionsInputFileName() const
Access to the attribute m_optionsInputFileName, which stores the name of the input file passed by the...
Definition: Environment.C:353
#define queso_error()
Definition: asserts.h:53
A class representing a vector space.
Definition: VectorSet.h:49
unsigned int numSimulations() const
Return number of simulations.
Definition: GPMSA.C:506
A class representing concatenated vector RVs.
This (virtual) class sets up the environment underlying the use of the QUESO library by an executable...
Definition: Environment.h:197
#define queso_assert_greater(expr1, expr2)
Definition: asserts.h:144
A templated base class for handling vector RV.
Definition: VectorRV.h:54
unsigned int numExperiments() const
Return number of experiments.
Definition: GPMSA.C:513
void setUpEmulator()
Definition: GPMSA.C:699
const V & simulationParameter(unsigned int simulationId) const
Return the point in parameterSpace for simulation simulationId.
Definition: GPMSA.C:567
A class representing a vector RV constructed via Gamma distribution.
Definition: GammaVectorRV.h:65
void setDiscrepancyBases(const std::vector< V * > &discrepancyBases)
Add all discrepancy bases to this.
Definition: GPMSA.C:918
virtual double lnValue(const V &domainVector, const V *domainDirection, V *gradVector, M *hessianMatrix, V *hessianEffect) const
Logarithm of the value of the scalar function.
Definition: GPMSA.C:94
void setUpHyperpriors()
Definition: GPMSA.C:975
#define queso_assert_greater_equal(expr1, expr2)
Definition: asserts.h:150
#define queso_require_less_msg(expr1, expr2, msg)
Definition: asserts.h:75
GPMSAEmulator(const VectorSet< V, M > &domain, const VectorSpace< V, M > &m_scenarioSpace, const VectorSpace< V, M > &m_parameterSpace, const VectorSpace< V, M > &m_simulationOutputSpace, const VectorSpace< V, M > &m_experimentOutputSpace, const unsigned int m_numSimulations, const unsigned int m_numExperiments, const std::vector< V * > &m_simulationScenarios, const std::vector< V * > &m_simulationParameters, const std::vector< V * > &m_simulationOutputs, const std::vector< V * > &m_experimentScenarios, const std::vector< V * > &m_experimentOutputs, const std::vector< V > &m_discrepancyBases, const std::vector< M > &m_observationErrorMatrices, const M &m_experimentErrors, const ConcatenatedVectorRV< V, M > &m_totalPrior, const V &residual_in, const M &BT_Wy_B_inv_in, const M &KT_K_inv_in)
Definition: GPMSA.C:32
A class for partitioning vectors and matrices.
Definition: Map.h:49
const V & simulationOutput(unsigned int simulationId) const
Return the simulation output for simulation simulationId.
Definition: GPMSA.C:586
int k
Definition: ann_sample.cpp:53
const VectorSpace< V, M > & m_experimentOutputSpace
Definition: GPMSA.h:314
Class representing a subset of a vector space shaped like a hypercube.
Definition: BoxSubset.h:44
void addSimulation(V &simulationScenario, V &simulationParameter, V &simulationOutput)
Add a simulation to this.
Definition: GPMSA.C:664
const BaseEnvironment & m_env
Definition: GPMSA.h:307
bool allocated_m_opts
Definition: GPMSA.h:454
const std::vector< V * > & simulationScenarios() const
Return all points in scenarioSpace for all simulations.
Definition: GPMSA.C:560
const VectorSpace< V, M > & simulationOutputSpace() const
Return the vector space in which simulations live.
Definition: GPMSA.C:534
virtual double actualValue(const V &domainVector, const V *domainDirection, V *gradVector, M *hessianMatrix, V *hessianEffect) const
Actual value of the scalar function.
Definition: GPMSA.C:414
GPMSAFactory(const BaseEnvironment &env, GPMSAOptions *opts, const BaseVectorRV< V, M > &parameterPrior, const VectorSpace< V, M > &scenarioSpace, const VectorSpace< V, M > &parameterSpace, const VectorSpace< V, M > &simulationOutputSpace, const VectorSpace< V, M > &experimentOutputSpace, unsigned int numSimulations, unsigned int numExperiments)
Constructor.
Definition: GPMSA.C:425
#define queso_assert_equal_to(expr1, expr2)
Definition: asserts.h:135
bool queso_isnan(T arg)
Definition: math_macros.h:39
virtual ~GPMSAEmulator()
Definition: GPMSA.C:87
A templated class for handling sets.
Definition: VectorSet.h:52
const VectorSpace< V, M > & scenarioSpace() const
Return the vector space in which scenarios live.
Definition: GPMSA.C:520
#define queso_assert(asserted)
Definition: asserts.h:132
const V & experimentScenario(unsigned int experimentId) const
Return the point in scenarioSpace for experiment experimentId.
Definition: GPMSA.C:605
This class defines the options that specify the behaviour of the Gaussian process emulator...
Definition: GPMSAOptions.h:43
const std::vector< V * > & experimentScenarios() const
Return all points in scenarioSpace for all experiments.
Definition: GPMSA.C:617
const V & simulationScenario(unsigned int simulationId) const
Return the point in scenarioSpace for simulation simulationId.
Definition: GPMSA.C:548
unsigned int num_svd_terms
Definition: GPMSA.h:105
GPMSAOptions * m_opts
Definition: GPMSA.h:455
const BaseEnvironment & env() const
Return the QUESO environment.
Definition: GPMSA.C:650
double scalarProduct(const GslVector &x, const GslVector &y)
Definition: GslVector.C:1136
const M & experimentErrors() const
Return all observation error covarince matrices for all experiments.
Definition: GPMSA.C:643
#define queso_require_less_equal_msg(expr1, expr2, msg)
Definition: asserts.h:77
A class representing a uniform vector RV.
const std::vector< V * > & simulationParameters() const
Return all points in parameterSpace for all simulations.
Definition: GPMSA.C:579
#define queso_require_msg(asserted, msg)
Definition: asserts.h:69
unsigned int dimGlobal() const
Definition: VectorSpace.C:176
The QUESO MPI Communicator Class.
Definition: MpiComm.h:203
void addExperiments(const std::vector< V * > &experimentScenarios, const std::vector< V * > &experimentOutputs, const M *experimentErrors)
Add all experiments to this.
Definition: GPMSA.C:894
const std::vector< V * > & experimentOutputs() const
Return all points in experimentOutputSpace for all experiments.
Definition: GPMSA.C:636
#define queso_assert_less(expr1, expr2)
Definition: asserts.h:141
~GPMSAFactory()
Destructor.
Definition: GPMSA.C:498
void addSimulations(const std::vector< V * > &simulationScenarios, const std::vector< V * > &simulationParameters, const std::vector< V * > &simulationOutputs)
Adds multiple simulations to this.
Definition: GPMSA.C:684
#define queso_error_msg(msg)
Definition: asserts.h:47
const MpiComm & Comm() const
Access function for MpiComm communicator.
Definition: Map.C:131
const std::vector< V * > & simulationOutputs() const
Return all points in simulationOutputSpace for all simulations.
Definition: GPMSA.C:598
const GPMSAEmulator< V, M > & getGPMSAEmulator() const
Return the GPMSAEmulator likelihood object.
Definition: GPMSA.C:657
const VectorSpace< V, M > & parameterSpace() const
Return the vector space in which parameters live.
Definition: GPMSA.C:527
const VectorSpace< V, M > & experimentOutputSpace() const
Return the vector space in which experiments live.
Definition: GPMSA.C:541
std::vector< M > m_observationErrorMatrices
Definition: GPMSA.h:330
unsigned int dimLocal() const
Definition: VectorSpace.C:170
const V & experimentOutput(unsigned int experimentId) const
Return the experiment output for experiment experimentId.
Definition: GPMSA.C:624

Generated on Tue Nov 29 2016 10:53:10 for queso-0.56.0 by  doxygen 1.8.5