From 610ae314b752b6d8bace16dd8a50421c7b987552 Mon Sep 17 00:00:00 2001
From: andy <a.heather@opencfd.co.uk>
Date: Wed, 20 Oct 2010 09:42:14 +0100
Subject: [PATCH] ENH: Added cachedRandom class

---
 src/OpenFOAM/Make/files                       |   1 +
 .../random/cachedRandom/cachedRandom.C        | 159 +++++++++++++++
 .../random/cachedRandom/cachedRandom.H        | 182 ++++++++++++++++++
 .../random/cachedRandom/cachedRandomI.H       |  55 ++++++
 .../cachedRandom/cachedRandomTemplates.C      |  65 +++++++
 5 files changed, 462 insertions(+)
 create mode 100644 src/OpenFOAM/primitives/random/cachedRandom/cachedRandom.C
 create mode 100644 src/OpenFOAM/primitives/random/cachedRandom/cachedRandom.H
 create mode 100644 src/OpenFOAM/primitives/random/cachedRandom/cachedRandomI.H
 create mode 100644 src/OpenFOAM/primitives/random/cachedRandom/cachedRandomTemplates.C

diff --git a/src/OpenFOAM/Make/files b/src/OpenFOAM/Make/files
index 32249f8da4e..531202fc8ec 100644
--- a/src/OpenFOAM/Make/files
+++ b/src/OpenFOAM/Make/files
@@ -62,6 +62,7 @@ $(sha1)/SHA1.C
 $(sha1)/SHA1Digest.C
 
 primitives/random/Random/Random.C
+primitives/random/cachedRandom/cachedRandom.H
 
 containers/HashTables/HashTable/HashTableCore.C
 containers/HashTables/StaticHashTable/StaticHashTableCore.C
diff --git a/src/OpenFOAM/primitives/random/cachedRandom/cachedRandom.C b/src/OpenFOAM/primitives/random/cachedRandom/cachedRandom.C
new file mode 100644
index 00000000000..3865f60fe11
--- /dev/null
+++ b/src/OpenFOAM/primitives/random/cachedRandom/cachedRandom.C
@@ -0,0 +1,159 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | Copyright (C) 2010-2010 OpenCFD Ltd.
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software; you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by the
+    Free Software Foundation; either version 2 of the License, or (at your
+    option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM; if not, write to the Free Software Foundation,
+    Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+
+\*---------------------------------------------------------------------------*/
+
+#include "cachedRandom.H"
+#include <cstdlib>
+
+#if INT_MAX    != 2147483647
+#    error "INT_MAX    != 2147483647"
+#    error "The random number generator may not work!"
+#endif
+
+// * * * * * * * * * * * * * private Member Functions  * * * * * * * * * * * //
+
+Foam::scalar Foam::cachedRandom::scalar01()
+{
+    if (sampleI_ < 0)
+    {
+        return drand48();
+    }
+
+    if (sampleI_ == samples_.size() - 1)
+    {
+        scalar s = samples_[sampleI_];
+        sampleI_ = 0;
+        return s;
+    }
+    else
+    {
+        scalar s = samples_[sampleI_];
+        sampleI_++;
+        return s;
+    }
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::cachedRandom::cachedRandom(const label seed, const label count)
+:
+    seed_(1),
+    samples_(0),
+    sampleI_(-1)
+{
+    if (seed > 1)
+    {
+        seed_ = seed;
+    }
+
+    // Samples will be cached if count > 0
+    if (count > 0)
+    {
+        samples_.setSize(count);
+        sampleI_ = 0;
+    }
+
+    // Initialise samples
+    srand48(seed_);
+    forAll(samples_, i)
+    {
+        samples_[i] = drand48();
+    }
+}
+
+
+Foam::cachedRandom::cachedRandom(const cachedRandom& cr, const bool reset)
+:
+    seed_(cr.seed_),
+    samples_(cr.samples_),
+    sampleI_(cr.sampleI_)
+{
+    if (sampleI_ == -1)
+    {
+        WarningIn
+        (
+            "Foam::cachedRandom::cachedRandom(const cachedRandom& cr)"
+        )   << "Copy constructor called, but samples not being cached. "
+            << "This may lead to non-repeatable behaviour" << endl;
+
+        srand48(seed_);
+    }
+    else if (reset)
+    {
+        sampleI_ = 0;
+    }
+}
+
+
+// * * * * * * * * * * * * * * * * Destructor  * * * * * * * * * * * * * * * //
+
+Foam::cachedRandom::~cachedRandom()
+{}
+
+
+// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
+
+template<>
+Foam::label Foam::cachedRandom::sample01()
+{
+    return round(scalar01());
+}
+
+
+template<>
+Foam::scalar Foam::cachedRandom::sample01()
+{
+    return scalar01();
+}
+
+
+template<>
+Foam::label Foam::cachedRandom::position(const label& start, const label& end)
+{
+    return start + round(scalar01()*(end - start));
+}
+
+
+template<>
+Foam::scalar Foam::cachedRandom::position
+(
+    const scalar& start,
+    const scalar& end
+)
+{
+    return start + scalar01()*(end - start);
+}
+
+
+void Foam::cachedRandom::operator=(const cachedRandom& cr)
+{
+    seed_ = cr.seed_;
+    samples_ = cr.samples_;
+    sampleI_ = cr.sampleI_;
+}
+
+
+// ************************************************************************* //
diff --git a/src/OpenFOAM/primitives/random/cachedRandom/cachedRandom.H b/src/OpenFOAM/primitives/random/cachedRandom/cachedRandom.H
new file mode 100644
index 00000000000..76da5228e6f
--- /dev/null
+++ b/src/OpenFOAM/primitives/random/cachedRandom/cachedRandom.H
@@ -0,0 +1,182 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | Copyright (C) 2010-2010 OpenCFD Ltd.
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software; you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by the
+    Free Software Foundation; either version 2 of the License, or (at your
+    option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM; if not, write to the Free Software Foundation,
+    Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+
+Class
+    Foam::cachedRandom
+
+Description
+    Random number generator.
+
+    Pre-computes and caches samples on construction, so that when sample01()
+    is called, the function simply returns the next (pre-computed) sample. On
+    reaching the last sample, the sample sequence is repeated.
+
+    Constructed using a seed and sample count. If the supplied count is
+    negative, no caching is performed, and a new sample is generated on each
+    call to sample01().
+
+    Note: the copy constructor cannot be used if count = -1.
+
+SourceFiles
+    cachedRandomI.H
+    cachedRandom.C
+    cachedRandomTemplates.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef cachedRandom_H
+#define cachedRandom_H
+
+#include "scalarList.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+// Forward declaration of classes
+class cachedRandom;
+
+/*---------------------------------------------------------------------------*\
+                       Class cachedRandom Declaration
+\*---------------------------------------------------------------------------*/
+
+class cachedRandom
+{
+private:
+
+    // Private data
+
+        //- Initial random number seed
+        label seed_;
+
+        //- List of scalar samples
+        scalarList samples_;
+
+        //- Current sample marker
+        label sampleI_;
+
+
+    // Private Member Functions
+
+        //- Returns the current sample
+        scalar scalar01();
+
+
+public:
+
+
+    // Constructors
+
+        //- Construct given seed and sample count
+        cachedRandom(const label seed, const label count);
+
+        //- Copy constructor with optional reset of sampleI
+        cachedRandom(const cachedRandom& cr, const bool reset = false);
+
+
+    // Destructor
+    ~cachedRandom();
+
+
+    // Member functions
+
+        // Access
+
+            //- Return const access to the initial random number seed
+            inline label seed() const;
+
+            //- Return const access to the list of samples
+            inline const scalarList& samples() const;
+
+            //- Return the current sample marker
+            inline label sampleI() const;
+
+
+        // Manipulation
+
+            //- Return non-const access to the sample marker
+            inline label& sampleI();
+
+
+        // Evaluation
+
+            //- Return a sample whose components lie in the range 0-1
+            template<class Type>
+            Type sample01();
+
+            //- Return a sample between start and end
+            template<class Type>
+            Type position(const Type& start, const Type& end);
+
+            //- Randomise value in the range 0-1
+            template<class Type>
+            void randomise01(Type& value);
+
+
+        // Operators
+
+            //- Assignment operator
+            void operator=(const cachedRandom& cr);
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+// Template specialisations
+
+template<>
+label cachedRandom::sample01<label>();
+
+template<>
+scalar cachedRandom::sample01<scalar>();
+
+template<>
+label cachedRandom::position<label>(const label& start, const label& end);
+
+template<>
+scalar cachedRandom::position<scalar>
+(
+    const scalar& start,
+    const scalar& end
+);
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#include "cachedRandomI.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#ifdef NoRepository
+#   include "cachedRandomTemplates.C"
+#endif
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/OpenFOAM/primitives/random/cachedRandom/cachedRandomI.H b/src/OpenFOAM/primitives/random/cachedRandom/cachedRandomI.H
new file mode 100644
index 00000000000..32bf5acf456
--- /dev/null
+++ b/src/OpenFOAM/primitives/random/cachedRandom/cachedRandomI.H
@@ -0,0 +1,55 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | Copyright (C) 2010-2010 OpenCFD Ltd.
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software; you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by the
+    Free Software Foundation; either version 2 of the License, or (at your
+    option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM; if not, write to the Free Software Foundation,
+    Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+
+\*---------------------------------------------------------------------------*/
+
+#include "cachedRandom.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+inline Foam::label Foam::cachedRandom::seed() const
+{
+    return seed_;
+}
+
+
+inline const Foam::scalarList& Foam::cachedRandom::samples() const
+{
+    return samples_;
+}
+
+
+inline Foam::label Foam::cachedRandom::sampleI() const
+{
+    return sampleI_;
+}
+
+
+inline Foam::label& Foam::cachedRandom::sampleI()
+{
+    return sampleI_;
+}
+
+
+// ************************************************************************* //
diff --git a/src/OpenFOAM/primitives/random/cachedRandom/cachedRandomTemplates.C b/src/OpenFOAM/primitives/random/cachedRandom/cachedRandomTemplates.C
new file mode 100644
index 00000000000..727450b0c2d
--- /dev/null
+++ b/src/OpenFOAM/primitives/random/cachedRandom/cachedRandomTemplates.C
@@ -0,0 +1,65 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | Copyright (C) 2010-2010 OpenCFD Ltd.
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software; you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by the
+    Free Software Foundation; either version 2 of the License, or (at your
+    option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM; if not, write to the Free Software Foundation,
+    Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+
+\*---------------------------------------------------------------------------*/
+
+#include "cachedRandom.H"
+
+// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
+
+template<class Type>
+Type Foam::cachedRandom::sample01()
+{
+    Type value;
+    for (direction cmpt=0; cmpt<pTraits<Type>::nComponents; cmpt++)
+    {
+        value.component(cmpt) = scalar01();
+    }
+
+    return value;
+}
+
+
+template<class Type>
+Type Foam::cachedRandom::position(const Type& start, const Type& end)
+{
+    Type value(start);
+    for (direction cmpt=0; cmpt<pTraits<Type>::nComponents; cmpt++)
+    {
+        value.component(cmpt) +=
+            scalar01()*(end.component(cmpt) - start.component(cmpt));
+    }
+
+    return value;
+}
+
+
+template<class Type>
+void Foam::cachedRandom::randomise01(Type& value)
+{
+    value = sample01<Type>();
+}
+
+
+// ************************************************************************* //
-- 
GitLab