Main Page | Namespace List | Class Hierarchy | Compound List | File List | Namespace Members | Compound Members | File Members

abkseed.h

Go to the documentation of this file.
00001 /**************************************************************************
00002 ***    
00003 *** Copyright (c) 1995-2000 Regents of the University of California,
00004 ***               Andrew E. Caldwell, Andrew B. Kahng and Igor L. Markov
00005 *** Copyright (c) 2000-2004 Regents of the University of Michigan,
00006 ***               Saurabh N. Adya, Jarrod A. Roy and Igor L. Markov
00007 ***
00008 ***  Contact author(s): abk@cs.ucsd.edu, imarkov@umich.edu
00009 ***  Original Affiliation:   UCLA, Computer Science Department,
00010 ***                          Los Angeles, CA 90095-1596 USA
00011 ***
00012 ***  Permission is hereby granted, free of charge, to any person obtaining 
00013 ***  a copy of this software and associated documentation files (the
00014 ***  "Software"), to deal in the Software without restriction, including
00015 ***  without limitation 
00016 ***  the rights to use, copy, modify, merge, publish, distribute, sublicense, 
00017 ***  and/or sell copies of the Software, and to permit persons to whom the 
00018 ***  Software is furnished to do so, subject to the following conditions:
00019 ***
00020 ***  The above copyright notice and this permission notice shall be included
00021 ***  in all copies or substantial portions of the Software.
00022 ***
00023 *** THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 
00024 *** EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
00025 *** OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 
00026 *** IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
00027 *** CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT
00028 *** OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR
00029 *** THE USE OR OTHER DEALINGS IN THE SOFTWARE.
00030 ***
00031 ***
00032 ***************************************************************************/
00033 
00034 
00035 
00036 
00038 
00039 #ifndef _ABKSEED_H_
00040 #define _ABKSEED_H_
00041 
00042 //#include <stl_config.h>
00043 #include <stdlib.h>
00044 #include <math.h>
00045 #include <fstream>
00046 #include <limits.h>
00047 #include <map>
00048 #include <string>
00049 
00050 using std::ifstream;
00051 using std::ofstream;
00052 
00053 //: Maintains all random seeds used by a process.
00054 //Idea:  First time you create a random object, an initial nondeterministic
00055 //       seed (also called the "external seed" is created from system
00056 //       information and logged to seeds.out.
00057 //       Any random object created with a seed of UINT_MAX ("nondeterministic"),
00058 //       and that does not use the snazzy new "local independence" feature,
00059 //       then uses seeds from a sequence starting with the initial value
00060 //       and increasing by 1 with each new nondeterministic random object
00061 //       created.
00062 //
00063 //       If the seed is overridden with a value other than UINT_MAX it is used,
00064 //       and logged to seeds.out .
00065 //
00066 //       However if seeds.in exists, the initial nondeterministic value
00067 //       is taken from the second line of seeds.in rather than the system
00068 //       clock, and subsequent *deterministic* values are taken from successive
00069 //       lines of seeds.in rather than from the value passed.
00070 //
00071 //       If seeds.out is in use or other errors occur trying to create it,
00072 //       a warning is generated that the seeds will not be logged, and
00073 //       the initial nondeterministic seed is printed (which should be
00074 //       sufficient to recreate the run provided that all "deterministic"
00075 //       seeds truly *are* deterministic (e.g. don't depend on external
00076 //       devices).
00077 //
00078 //       You can disable the logging function by calling the static
00079 //       function SeedHandler::turnOffLogging().  This will not disable
00080 //       the ability to override seeding with seeds.in .
00081 //NEW ULTRA-COOL FEATURE: (17 June 1999)
00082 //       You now have the option, which I (Mike) highly recommend,
00083 //       of specifying, instead of a seed, a "local identifier", which
00084 //       is a string that should identify uniquely the random variable
00085 //       (not necessarily the random object) being used.  The suggested
00086 //       format of this string is as follows: If your
00087 //       RNG is called _rng and is a member of MyClass, pass
00088 //       the string "MyClass::_rng".  If it's a local variable
00089 //       called rng in the method MyClass::myMethod(), pass
00090 //       the string "MyClass::myMethod(),_rng".
00091 //
00092 //       SeedHandler will maintain a collection of counters associated
00093 //       with each of these strings.  The sequence of random numbers
00094 //       from a random object will be determined by three things:
00095 //            1) the "external seed" (same as "initial nondeterm seed").
00096 //            2) the "local identifier" (the string described above).
00097 //            3) the counter saying how many RNG objects have previously
00098 //                 been created with the same local identifier.
00099 //       When any one of these changes, the output should be effectively
00100 //       independent of the previous RNG.  Moreover you don't have
00101 //       to worry about your regressions changing simply because someone
00102 //       else's code which you call has changed the number of RNG objects
00103 //       it uses.
00104 //ANOTHER NEW FEATURE (21 February 2001)
00105 //       At times you may wish to control the external seed yourself, e.g.
00106 //       by specifying the seed on the command line, rather than
00107 //       using either seeds.in or the nondeterministic chooser.
00108 //       To enable this, a static method SeedHandler::overrideExternalSeed()
00109 //       has been added.  If you call this method before any random
00110 //       object has been created, you can set the external seed.
00111 //       The file seeds.out will still be created unless you call
00112 //       SeedHandler::turnOffLogging().  If seeds.in exists, it
00113 //       will control -- your call to overrideExternalSeed() will
00114 //       print a warning message and otherwise be ignored.
00115 
00116 struct SeedHandlerCompareStrings
00117     {
00118     bool operator()(std::string firstString, std::string secondString) const
00119         {
00120         return strcmp(firstString.c_str(), secondString.c_str()) < 0;
00121         }
00122     };
00123 class SeedHandler
00124     {
00125     private:
00126         SeedHandler(unsigned seed);
00127         
00128         SeedHandler(const char *locIdent,
00129             unsigned counterOverride=UINT_MAX);
00130 
00131     public:
00132 
00133         ~SeedHandler();
00134 
00135     private:
00136 
00137         void _init();
00138         
00139         unsigned _seed;
00140         
00141         char    *_locIdent;
00142         unsigned _counter;
00143         bool     _isSeedMultipartite;
00144         
00145         static ofstream *_PseedOutFile;
00146         static ifstream *_PseedInFile;
00147         static unsigned _nextSeed; 
00148         // slight misnomer,  This is the next nondeterministic seed.
00149         
00150         static unsigned _externalSeed;
00151         static unsigned _progOverrideExternalSeed;
00152         
00153         static std::map<std::string,unsigned,SeedHandlerCompareStrings >
00154             _counters;
00155         
00156         static bool _loggingOff;            
00157         // don't log seeds
00158         static bool _haveRandObj;          
00159         // starts false, true after first 
00160         static bool _cleaned;               
00161         // clean() has been called  
00162         void _chooseInitNondetSeed();        
00163         // first nondeterministic seed thereafter, increment.
00164         void _initializeOutFile();           
00165         //  create log file and write first two lines.
00166         
00167         
00168         friend class RandomRoot;
00169         friend class SeedCleaner;
00170     public:
00171         static void turnOffLogging();
00172         static void overrideExternalSeed(unsigned extseed);
00173                 static bool isInitialized() { return _haveRandObj; }
00174     private:
00175         static void clean();
00176     };
00177 
00178     /* One global object of the following class, declared in seeds.cxx, will
00179 make sure that SeedHandler::clean() is called at the end of execution*/
00180 //: Makes it sure that SeedHandler will be cleaned at the end of execution
00181 class SeedCleaner
00182     {
00183     public:
00184         SeedCleaner(){}
00185         
00186         ~SeedCleaner(){SeedHandler::clean();}
00187     };
00188 
00189 #endif

Generated on Mon Apr 25 01:09:23 2005 for Parquete by doxygen 1.3.2