/*========================================================================= Program: Visualization Toolkit Module: vtkMinimalStandardRandomSequence.h Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen All rights reserved. See Copyright.txt or http://www.kitware.com/Copyright.htm for details. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the above copyright notice for more information. =========================================================================*/ /** * @class vtkMinimalStandardRandomSequence * @brief Park and Miller Sequence of pseudo random numbers * * vtkMinimalStandardRandomSequence is a sequence of statistically independent * pseudo random numbers uniformly distributed between 0.0 and 1.0. * * The sequence is generated by a prime modulus multiplicative linear * congruential generator (PMMLCG) or "Lehmer generator" with multiplier 16807 * and prime modulus 2^(31)-1. The authors calls it * "minimal standard random number generator" * * ref: "Random Number Generators: Good Ones are Hard to Find," * by Stephen K. Park and Keith W. Miller in Communications of the ACM, * 31, 10 (Oct. 1988) pp. 1192-1201. * Code is at page 1195, "Integer version 2" * * Correctness test is described in first column, page 1195: * A seed of 1 at step 1 should give a seed of 1043618065 at step 10001. */ #ifndef vtkMinimalStandardRandomSequence_h #define vtkMinimalStandardRandomSequence_h #include "vtkCommonCoreModule.h" // For export macro #include "vtkRandomSequence.h" class VTKCOMMONCORE_EXPORT vtkMinimalStandardRandomSequence : public vtkRandomSequence { public: ///@{ /** * Standard methods for instantiation, type information, and printing. */ static vtkMinimalStandardRandomSequence* New(); vtkTypeMacro(vtkMinimalStandardRandomSequence, vtkRandomSequence); void PrintSelf(ostream& os, vtkIndent indent) override; ///@} /** * Satisfy general API of vtkRandomSequence superclass. Initialize the * sequence with a seed. */ void Initialize(vtkTypeUInt32 seed) override { this->SetSeed(seed); } /** * Set the seed of the random sequence. * The following pre-condition is stated page 1197, second column: * valid_seed: value>=1 && value<=2147483646 * 2147483646=(2^31)-2 * This method does not have this criterium as a pre-condition (ie it will * not fail if an incorrect seed value is passed) but the value is silently * changed to fit in the valid range [1,2147483646]. * 2147483646 is added to a null or negative value. * 2147483647 is changed to be 1 (ie 2147483646 is subtracted). * Implementation note: it also performs 3 calls to Next() to avoid the * bad property that the first random number is proportional to the seed * value. */ void SetSeed(int value); /** * Set the seed of the random sequence. There is no extra internal * adjustment. Only useful for writing correctness test. * The following pre-condition is stated page 1197, second column * 2147483646=(2^31)-2 * This method does not have this criterium as a pre-condition (ie it will * not fail if an incorrect seed value is passed) but the value is silently * changed to fit in the valid range [1,2147483646]. * 2147483646 is added to a null or negative value. * 2147483647 is changed to be 1 (ie 2147483646 is subtracted). */ void SetSeedOnly(int value); /** * Get the seed of the random sequence. * Only useful for writing correctness test. */ int GetSeed(); /** * Current value * \post unit_range: result>=0.0 && result<=1.0 */ double GetValue() override; /** * Move to the next number in the random sequence. */ void Next() override; /** * Convenient method to return a value in a specific range from the * range [0,1. There is an initial implementation that can be overridden * by a subclass. * There is no pre-condition on the range: * - it can be in increasing order: rangeMinrangeMax * \post result_in_range: * (rangeMin<=rangeMax && result>=rangeMin && result<=rangeMax) * || (rangeMax<=rangeMin && result>=rangeMax && result<=rangeMin) */ virtual double GetRangeValue(double rangeMin, double rangeMax); /** * Get the next value in the sequence within a range. * * \see vtkMinimalStandardRandomSequence::GetRangeValue */ double GetNextRangeValue(double rangeMin, double rangeMax); protected: vtkMinimalStandardRandomSequence(); ~vtkMinimalStandardRandomSequence() override; int Seed; private: vtkMinimalStandardRandomSequence(const vtkMinimalStandardRandomSequence&) = delete; void operator=(const vtkMinimalStandardRandomSequence&) = delete; }; #endif // #ifndef vtkMinimalStandardRandomSequence_h