SSJ API Documentation
Stochastic Simulation in Java
Loading...
Searching...
No Matches
ArrayOfComparableChains.java
1package umontreal.ssj.markovchainrqmc;
2
3import umontreal.ssj.stat.PgfDataTable;
4import umontreal.ssj.stat.Tally;
5import umontreal.ssj.util.*;
6import umontreal.ssj.util.multidimsort.*;
7import umontreal.ssj.hups.*;
8import umontreal.ssj.charts.*;
9import umontreal.ssj.functionfit.LeastSquares;
10import java.io.IOException;
11import java.io.Writer;
12import java.io.FileWriter;
13import java.lang.reflect.Array;
14
75 protected T baseChain; // The base chain.
76 protected int n; // Current number of chains.
77 // protected int stateDim; // Dimension of the chain state.
78 protected T[] chains; // Array of n comparable chains.
79 protected double[] performances; // Performances for the n chains.
80 protected PointSetRandomization randomization;
81 protected MultiDimSort<T> savedSort;
82 protected int sortCoordPts = 0; // Point coordinates used to sort points.
83
88
94 public ArrayOfComparableChains(T baseChain) {
95 this.baseChain = baseChain;
96 // stateDim = baseChain.stateDim;
97 }
98
106 this.baseChain = baseChain;
107 // stateDim = baseChain.stateDim;
108 randomization = rand;
109 savedSort = sort;
110 }
111
116 @SuppressWarnings("unchecked")
117 public void makeCopies(int n) {
118
119 final T[] c = (T[]) Array.newInstance(baseChain.getClass(), n);
120 chains = c; // Array of Markov chains.
121
122 this.n = n;
123 performances = new double[n]; // Array to store the performances.
124 for (int i = 0; i < n; i++) {
125 try {
126 chains[i] = (T) baseChain.clone();
127 } catch (CloneNotSupportedException e) {
128 System.err.println("ArrayOfComparableChains:");
129 e.printStackTrace();
130 }
131 }
132 }
133
140 public void initialStates() {
141 int i = 0;
142 for (T mc : chains) {
143 mc.initialState();
144 performances[i] = mc.getPerformance(); // Needed? Why do this?
145 ++i;
146 }
147 }
148
152 public int getN() {
153 return n;
154 }
155
159 public T[] getChains() {
160 return chains;
161 }
162
167 randomization = rand;
168 }
169
174 return randomization;
175 }
176
180 public void setSort(MultiDimSort<T> sort) {
181 savedSort = sort;
182 }
183
188 return savedSort;
189 }
190
208 public int simulOneStepArrayRQMC(PointSet p, PointSetRandomization rand, MultiDimSort<T> sort, int sortCoordPts) {
209 int nStopped = 0;
210 p.randomize(rand); // Randomize point set.
211 if (sortCoordPts > 0) {
212 if (!(p instanceof CachedPointSet))
213 throw new IllegalArgumentException("p is not a CachedPointSet.");
214 if (sortCoordPts > 1)
215 ((CachedPointSet) p).sort(sort); // Sort points using first sortCoordPts coordinates.
216 else
217 ((CachedPointSet) p).sortByCoordinate(0); // Sort by first coordinate.
218 }
219 PointSetIterator stream = p.iterator();
220 stream.resetCurPointIndex(); // Go to first point.
221 int i = 0;
222 for (T mc : chains) { // Assume the chains are sorted
223 if (mc.hasStopped()) {
224 ++nStopped;
225 } else {
226 stream.setCurCoordIndex(sortCoordPts); // Skip first sortCoordPts coord.
227 mc.nextStep(stream); // simulate next step of the chain.
228 stream.resetNextSubstream(); // Go to next point.
229 if (mc.hasStopped())
230 ++nStopped;
231 }
232 performances[i] = mc.getPerformance();
233 ++i;
234 }
235 return n - nStopped;
236 }
237
243 return simulOneStepArrayRQMC(p, randomization, savedSort, 0);
244 }
245
267 public double simulArrayRQMC(PointSet p, PointSetRandomization rand, MultiDimSort<T> sort, int sortCoordPts,
268 int numSteps) {
269 int numNotStopped = n;
271 int step = 0;
272 while (step < numSteps && numNotStopped > 0) {
273 if (numNotStopped == n)
274 sort.sort(chains, 0, n);
275 else
276 sortNotStoppedChains(sort); // Sort the numNotStopped first chains.
277 p.randomize(rand); // Randomize the point set.
278 if (sortCoordPts > 0) {
279 if (!(p instanceof CachedPointSet))
280 throw new IllegalArgumentException("p is not a CachedPointSet.");
281 if (sortCoordPts > 1)
282 ((CachedPointSet) p).sort(sort); // Sort points using first sortCoordPts coordinates.
283 else
284 ((CachedPointSet) p).sortByCoordinate(0); // Sort by first coordinate.
285 }
286 PointSetIterator stream = p.iterator();
287 stream.resetCurPointIndex(); // Go to first point.
288 int i = 0;
289 for (T mc : chains) { // Assume the chains are sorted
290 if (mc.hasStopped()) {
291 numNotStopped--;
292 } else {
293 stream.setCurCoordIndex(sortCoordPts); // Skip first sortCoordPts coord.
294 mc.nextStep(stream); // simulate next step of the chain.
295 stream.resetNextSubstream(); // Go to next point.
296 if (mc.hasStopped())
297 numNotStopped--;
298 }
299 performances[i] = mc.getPerformance();
300 ++i;
301 }
302 ++step;
303 }
304 return calcMeanPerf();
305 }
306
311 public double simulArrayRQMC(PointSet p, PointSetRandomization rand, MultiDimSort<T> sort, int numSteps) {
312 return simulArrayRQMC(p, rand, sort, 0, numSteps);
313 }
314
319 public double simulArrayRQMC(PointSet p, int numSteps) {
320 return simulArrayRQMC(p, randomization, savedSort, 0, numSteps);
321 }
322
326 public double[] getPerformances() {
327 return performances;
328 }
329
333 public double calcMeanPerf() {
334 double sumPerf = 0.0; // Sum of performances.
335 for (int i = 0; i < n; ++i) {
336 sumPerf += performances[i];
337 }
338 return sumPerf / n;
339 }
340
346 public void simulReplicatesArrayRQMC(PointSet p, PointSetRandomization rand, MultiDimSort<T> sort, int sortCoordPts,
347 int numSteps, int m, Tally statReps) {
349 statReps.init();
350 for (int rep = 0; rep < m; rep++) {
351 statReps.add(simulArrayRQMC(p, rand, sort, sortCoordPts, numSteps));
352 }
353 }
354
362 int sortCoordPts, int numSteps, int m, Tally statReps) {
365 timer.init();
366 statReps.init();
367 for (int rep = 0; rep < m; rep++) {
368 statReps.add(simulArrayRQMC(p, rand, sort, sortCoordPts, numSteps));
369 }
370 StringBuffer sb = new StringBuffer("----------------------------------------------" + PrintfFormat.NEWLINE);
371 sb.append("Array-RQMC simulations:" + PrintfFormat.NEWLINE);
372 sb.append(PrintfFormat.NEWLINE + p.toString() + ":" + PrintfFormat.NEWLINE);
373 sb.append(" Number of indep copies m = " + m);
374 sb.append(PrintfFormat.NEWLINE + " Number of points n = " + n + PrintfFormat.NEWLINE);
375 sb.append(baseChain.formatResultsRQMC(statReps, n));
376 sb.append(" CPU Time = " + timer.format() + PrintfFormat.NEWLINE);
377 return sb.toString();
378 }
379
384 public String varianceImprovementFormat(double varRQMC, double varMC) {
385 // double varRQMC = p.getNumPoints() * statReps.variance();
386 StringBuffer sb = new StringBuffer(
387 " Variance ratio MC / RQMC: " + PrintfFormat.format(15, 10, 4, varMC / varRQMC) + PrintfFormat.NEWLINE);
388 return sb.toString();
389 }
390
405 int sortCoordPts, int numSteps, int m, double varMC, String filenamePlot, String methodLabel) {
406
407 int numSets = pointSets.length; // Number of point sets.
408 Tally statPerf = new Tally("Performance");
409 double[] logn = new double[numSets];
410 double[] variance = new double[numSets];
411 double[] logVariance = new double[numSets];
412 long initTime; // For timings.
413
414 StringBuffer str = new StringBuffer("\n\n --------------------------");
415 str.append(methodLabel + "\n MC Variance : " + varMC + "\n\n");
416
417 // Array-RQMC experiment with each pointSet.
418 for (int i = 0; i < numSets; ++i) {
419 initTime = System.currentTimeMillis();
420 n = pointSets[i].getNumPoints();
421 str.append("n = " + n + "\n");
422 simulReplicatesArrayRQMC(pointSets[i], rand, sort, sortCoordPts, numSteps, m, statPerf);
423 logn[i] = Num.log2(n);
424 variance[i] = statPerf.variance();
425 logVariance[i] = Num.log2(variance[i]);
426 str.append(" Average = " + statPerf.average() + "\n");
427 str.append(" VRF = " + varMC / (n * variance[i]) + "\n");
428 str.append(formatTime((System.currentTimeMillis() - initTime) / 1000.) + "\n");
429 }
430 // Estimate regression slope and print plot and overall results.
431 double regSlope = slope(logn, logVariance, numSets);
432 str.append("Regression slope (log) for variance = " + regSlope + "\n\n");
433
434 // Print plot and overall results in files.
435 if (filenamePlot != null)
436 try {
437 Writer file = new FileWriter(filenamePlot + ".tex");
438 XYLineChart chart = new XYLineChart();
439 // ("title", "$log_2(n)$", "$log_2 Var[hat mu_{rqmc,s,n}]$");
440 chart.add(logn, logVariance);
441 file.write(chart.toLatex(12, 8));
442 file.close();
443 } catch (IOException e) {
444 e.printStackTrace();
445 }
446 return str.toString();
447 }
448
463 public String testVarianceRateFormat(RQMCPointSet[] rqmcPts, MultiDimSort<T> sort, int sortCoordPts, int numSteps,
464 int m, double varMC, String filenamePlot, String methodLabel) {
465 int numSets = rqmcPts.length; // Number of point sets.
466 Tally statPerf = new Tally("Performance");
467 double[] logn = new double[numSets];
468 double[] variance = new double[numSets];
469 double[] logVariance = new double[numSets];
470 long initTime; // For timings.
471
472 StringBuffer str = new StringBuffer("\n\n --------------------------");
473 str.append(methodLabel + "\n MC Variance per Run : " + varMC / (double) n + "\n\n");
474
475 // Array-RQMC experiment with each pointSet.
476 for (int i = 0; i < numSets; ++i) {
477
478// performancePerRun = new Tally[numSteps];
479 for (int j = 0; j < numSteps; ++j)
480 performancePerRun[j] = new Tally();
481 initTime = System.currentTimeMillis();
482 n = rqmcPts[i].getNumPoints();
483 str.append("n = " + n + "\n");
484 simulReplicatesArrayRQMC(rqmcPts[i].getPointSet(), rqmcPts[i].getRandomization(), sort, sortCoordPts, numSteps,
485 m, statPerf);
486 logn[i] = Num.log2(n);
487 variance[i] = statPerf.variance();
488 logVariance[i] = Num.log2(variance[i]);
489 str.append(" Average = " + statPerf.average() + "\n");
490 str.append(" RQMC Variance : " + variance[i] + "\n\n");
491 str.append(" VRF = " + varMC / (n * variance[i]) + "\n");
492 str.append(formatTime((System.currentTimeMillis() - initTime) / 1000.) + "\n");
493 }
494 // Estimate regression slope and print plot and overall results.
495 double regSlope = slope(logn, logVariance, numSets);
496 str.append("Regression slope (log) for variance = " + regSlope + "\n\n");
497
498 String[] tableField = { "log(n)", "log(Var)" };
499 double[][] data = new double[numSets][2];
500 for (int s = 0; s < numSets; s++) { // For each cardinality n
501 data[s][0] = logn[s];
502 data[s][1] = logVariance[s];
503 }
504
505 // Print plot and overall results in files.
506 if (filenamePlot != null)
507 try {
508
509 PgfDataTable pgf = new PgfDataTable(filenamePlot, rqmcPts[0].getLabel(), tableField, data);
510 String pVar = pgf.drawPgfPlotSingleCurve(filenamePlot, "axis", 0, 1, 2, "", "");
511 String plotIV = (PgfDataTable.pgfplotFileHeader() + pVar + PgfDataTable.pgfplotEndDocument());
512
513 FileWriter fileIV = new FileWriter(filenamePlot + "_" + "VAr.tex");
514 fileIV.write(plotIV);
515 fileIV.close();
516 } catch (IOException e) {
517 e.printStackTrace();
518 }
519
520 tableField = new String[] { "step", "average", "variance" };
521 data = new double[numSteps][3];
522 for (int s = 0; s < numSteps; s++) { // For each cardinality n
523 data[s][0] = s + 1;
524 data[s][1] = performancePerRun[s].average();
525 data[s][2] = performancePerRun[s].variance();
526 }
527
528 if (filenamePlot != null)
529 try {
530
531 PgfDataTable pgf = new PgfDataTable(filenamePlot, rqmcPts[0].getLabel(), tableField, data);
532 String pMean = pgf.drawPgfPlotSingleCurve(filenamePlot, "axis", 0, 1, 2, "", "");
533 String pVar = pgf.drawPgfPlotSingleCurve(filenamePlot, "axis", 0, 2, 2, "", "");
534
535 String plotMean = (PgfDataTable.pgfplotFileHeader() + pMean + PgfDataTable.pgfplotEndDocument());
536 String plotVar = (PgfDataTable.pgfplotFileHeader() + pVar + PgfDataTable.pgfplotEndDocument());
537
538 FileWriter fileIV = new FileWriter(filenamePlot + "_" + "MeanPerStep.tex");
539 fileIV.write(plotMean);
540 fileIV.close();
541
542 fileIV = new FileWriter(filenamePlot + "_" + "VariancePerStep.tex");
543 fileIV.write(plotVar);
544 fileIV.close();
545 } catch (IOException e) {
546 e.printStackTrace();
547 }
548
549 return str.toString();
550 }
551
559 int j = n - 1;
560 int i = 0;
561 T mc;
562 while (j >= 0 && chains[j].hasStopped())
563 --j;
564 while (i < n && !chains[i].hasStopped())
565 ++i;
566 while (i < j) {
567 while (!chains[i].hasStopped())
568 ++i;
569 while (chains[j].hasStopped())
570 --j;
571 mc = chains[i];
572 chains[i] = chains[j];
573 chains[j] = mc;
574 }
575 sort.sort(chains, 0, i);
576 }
577
583 public void sortChains() {
584 savedSort.sort(chains, 0, n);
585 }
586
587 // Takes time in seconds and formats it.
588 public String formatTime(double time) {
589 int second, hour, min, centieme;
590 hour = (int) (time / 3600.0);
591 if (hour > 0) {
592 time -= ((double) hour * 3600.0);
593 }
594 min = (int) (time / 60.0);
595 if (min > 0) {
596 time -= ((double) min * 60.0);
597 }
598 second = (int) time;
599 centieme = (int) (100.0 * (time - (double) second) + 0.5);
600 return String.valueOf(hour) + ":" + min + ":" + second + "." + centieme;
601 }
602
603 // Compute slope of linear regression of y on x, using only first n
604 // observations.
605 public double slope(double[] x, double[] y, int n) {
606 if (n < 2) {
607 return 0.0;
608 } else {
609 double[] x2 = new double[n], y2 = new double[n];
610 for (int i = 0; i < n; ++i) {
611 x2[i] = x[i];
612 y2[i] = y[i];
613 }
614 return LeastSquares.calcCoefficients(x2, y2, 1)[1];
615 }
616 }
617}
Provides tools to create and manage curve plots.
This container class caches a point set by precomputing and storing all the points locally in an arra...
This abstract class represents a general point set.
Definition PointSet.java:99
void randomize(PointSetRandomization rand)
Randomizes this point set using the given rand.
PointSetIterator iterator()
Constructs and returns a point set iterator.
int getNumPoints()
Returns the number of points.
String toString()
Formats a string that contains information about the point set.
This class is used for randomized quasi-Monte Carlo (RQMC) simulations.
int getNumPoints()
Returns the number of points in the associated point set.
PointSetRandomization getRandomization()
Returns the internal umontreal.ssj.hups.PointSetRandomization.
double[] getPerformances()
Returns the vector for performances for the chains.
String varianceImprovementFormat(double varRQMC, double varMC)
Returns a string that reports the the ratio of MC variance per run varMC over the RQMC variance per r...
int simulOneStepArrayRQMC(PointSet p, PointSetRandomization rand, MultiDimSort< T > sort, int sortCoordPts)
Randomized the point set p and Simulates the copies of the chain, one step for each copy,...
int simulOneStepArrayRQMC(PointSet p)
This version uses the preselected randomization and sort, with sortCoordPts = 0.
Tally[] performancePerRun
Performance measure at each step of the chain.
double calcMeanPerf()
Computes and returns the mean performance of the chains.
double simulArrayRQMC(PointSet p, PointSetRandomization rand, MultiDimSort< T > sort, int numSteps)
This version assumes that sortCoordPts = 0, so that there is no need to sort the points at each step.
ArrayOfComparableChains(T baseChain, PointSetRandomization rand, MultiDimSort< T > sort)
Creates an array of the comparable chain baseChain.
void setRandomization(PointSetRandomization rand)
Sets the internal umontreal.ssj.hups.PointSetRandomization to rand.
void sortNotStoppedChains(MultiDimSort< T > sort)
Sorts the chains that have not stopped yet using the stored.
void setSort(MultiDimSort< T > sort)
Sets the internal umontreal.ssj.util.MultiDimSort to sort.
void initialStates()
Initializes the n copies (clones) of the chain baseChain to their initial state by calling initialSta...
void simulReplicatesArrayRQMC(PointSet p, PointSetRandomization rand, MultiDimSort< T > sort, int sortCoordPts, int numSteps, int m, Tally statReps)
Performs m independent replications of an array-RQMC simulation as in simulArrayRQMC.
ArrayOfComparableChains(T baseChain)
Creates an array of the comparable chain baseChain.
String testVarianceRateFormat(PointSet[] pointSets, PointSetRandomization rand, MultiDimSort< T > sort, int sortCoordPts, int numSteps, int m, double varMC, String filenamePlot, String methodLabel)
Performs an experiment to estimate the convergence rate of the RQMC variance as a function of ,...
double simulArrayRQMC(PointSet p, PointSetRandomization rand, MultiDimSort< T > sort, int sortCoordPts, int numSteps)
Simulates the copies of the chain, numSteps steps for each copy, using umontreal....
String simulReplicatesArrayRQMCFormat(PointSet p, PointSetRandomization rand, MultiDimSort< T > sort, int sortCoordPts, int numSteps, int m, Tally statReps)
Performs m independent replications of an array-RQMC simulation as in simulFormatArrayRQMC.
void makeCopies(int n)
Creates n copies (clones) of the chain baseChain and puts them in an array, ready for the array RQMC ...
String testVarianceRateFormat(RQMCPointSet[] rqmcPts, MultiDimSort< T > sort, int sortCoordPts, int numSteps, int m, double varMC, String filenamePlot, String methodLabel)
Same as above, but produces a plot of the mean and the variance as a function of the step.
double simulArrayRQMC(PointSet p, int numSteps)
This version assumes that sortCoordPts = 0 and uses the preset randomization and sort for the chains.
MultiDimSort< T > getSort()
Returns the saved umontreal.ssj.util.MultiDimSort.
T[] getChains()
Returns the underlying array of n MarkovChainComparable.
A subclass of MarkovChain for which there is a total ordering between the states, induced by the impl...
Represents a data table which has a name, a number of observations (rows), a number of fields (column...
String drawPgfPlotSingleCurve(String title, String axistype, String xaxis, String yaxis, int logbasis, String axisoptions, String plotoptions)
Returns a String that contains a complete tikzpicture for the pgfplot package, showing the field j2 a...
A subclass of StatProbe.
Definition Tally.java:47
double average()
Returns the average value of the observations since the last initialization.
Definition Tally.java:155
double variance()
Returns the sample variance of the observations since the last initialization.
Definition Tally.java:174
void init()
Initializes the statistical collector.
Definition Tally.java:91
void add(double x)
Gives a new observation x to the statistical collector.
Definition Tally.java:109
String format()
Converts the CPU time used by the program since its last call to init for this AbstractChrono to a St...
void init()
Initializes this AbstractChrono to zero.
The Chrono class extends the umontreal.ssj.util.AbstractChrono class and computes the CPU time for th...
Definition Chrono.java:37
static Chrono createForSingleThread()
Creates a Chrono instance adapted for a program using a single thread.
Definition Chrono.java:60
This class provides various constants and methods to compute numerical quantities such as factorials,...
Definition Num.java:35
static double log2(double x)
Returns x .
Definition Num.java:405
This class acts like a StringBuffer which defines new types of append methods.
static final String NEWLINE
End-of-line symbol or line separator.
static String format(long x)
Same as d(0, 1, x).
This is the interface for iterators that permit one to go through the points of a PointSet and the su...
void resetCurPointIndex()
Equivalent to setCurPointIndex(0).
void setCurCoordIndex(int j)
Sets the current coordinate index to , so that the next calls to nextCoordinate or nextCoordinates wi...
This interface is for a randomization that can be used to randomize a umontreal.ssj....
void resetNextSubstream()
Reinitializes the stream to the beginning of its next substream:
This interface is meant to be implemented by certain multivariate sorting algorithms that sort object...
void sort(T[] a, int iMin, int iMax)
Sorts the subarray of a made of the elements with indices from iMin to iMax-1.