Confusion about `Random`

jwatson-CO-edu real.name at colorado.edu
Fri Dec 23 15:07:27 UTC 2022


On Friday, 23 December 2022 at 00:58:01 UTC, Steven Schveighoffer 
wrote:
> Without the rest of the code, and how random is called, I have 
> a hunch... Are you using threads by any chance?
>
> If, for instance, your calls to rand01 are done in a new 
> thread, that new thread will have a *default* state of Mt19937.
> -Steve

Good question, Steve, but I do not intentionally start any 
threads.  Below is the machinery that interprets a for-loop.  Do 
you see anything that would enclose a previous state of the RNG?

```d
specialForms["for"] = function ExprInContext( ExprInContext eINc 
){
     // Execute a `for` loop, Default is to increment up by one

     // 1. Parse loop args
     Atom*[] loopArgs  = flatten_atom_list( second( eINc.expr ) ); 
// Fetch args
     string  iVarName  = loopArgs[0].str; //Get the counter var 
name
     bool    incrByOne = (loopArgs.length == 3);
     double  loBound   = 0.0;
     double  hiBound   = 0.0;
     double  incr      = 1.0;
     double  i /*---*/ = 0.0;
     Atom*   loopProg  = third( eINc.expr ); // WARNING: TYPE NOT 
CHECKED
     Atom*   rtnExpr   = null;
     Env*    nuEnv     = null;
     ExprInContext runBlock;


     // Case: Default loop increments by 1.0
     if( incrByOne ){
         loBound = loopArgs[1].num;
         hiBound = loopArgs[2].num;

     // Case: User-specified increment
     }else if(loopArgs.length == 4){
         loBound = loopArgs[1].num;
         incr    = loopArgs[2].num;
         hiBound = loopArgs[3].num;

     // Else: There is a syntax error
     }else  return ExprInContext(
         new Atom( F_Error.SYNTAX, loopArgs.length.to!string ~
                   " was an incorrect number of loop args. 
Expected 3 or 4." ),
         eINc.context,
         "`for` got an unexpected number of args"
     );

     // 2. Create a new nested context, bind the counter var
     i     = loBound;
     nuEnv = new Env();
     nuEnv.parent = eINc.context;
     bind_atom( nuEnv, iVarName, new Atom( loBound ) );

     runBlock = ExprInContext(
         loopProg,
         nuEnv,
         "loop body"
     );

     // 3. LOOP:
     while( i <= hiBound ){
         // run block in nested context
         rtnExpr = block_meaning( runBlock ).expr;
         i += incr; // increment
         // Store new counter value so that loop body can access it
         bind_atom( nuEnv, iVarName, new Atom( i ) );
     }

     return ExprInContext(
         rtnExpr,
         eINc.context,
         "loop result"
     );

};
```




More information about the Digitalmars-d-learn mailing list