Skip to content

Commit df00cd1

Browse files
committed
Restore backwards compatibility of Environment and remove unused default instance of PCG
1 parent 5b405ee commit df00cd1

File tree

3 files changed

+54
-42
lines changed

3 files changed

+54
-42
lines changed

SimSharp/Core/Environment.cs

Lines changed: 40 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -21,34 +21,6 @@ You should have received a copy of the GNU General Public License
2121
using System.IO;
2222

2323
namespace SimSharp {
24-
25-
/// <summary>
26-
/// Environments hold the event queues, schedule and process events.
27-
/// </summary>
28-
[Obsolete("Use class Simulation or ThreadSafeSimulation instead. Due to name clashes with System.Environment the class SimSharp.Environment is being outphased.")]
29-
public class Environment : ThreadSafeSimulation {
30-
public Environment()
31-
: base() {
32-
Random = new SystemRandom();
33-
}
34-
public Environment(TimeSpan? defaultStep)
35-
: base(defaultStep) {
36-
Random = new SystemRandom();
37-
}
38-
public Environment(int randomSeed, TimeSpan? defaultStep = null)
39-
: base(randomSeed, defaultStep) {
40-
Random = new SystemRandom(randomSeed);
41-
}
42-
public Environment(DateTime initialDateTime, TimeSpan? defaultStep = null)
43-
: base(initialDateTime, defaultStep) {
44-
Random = new SystemRandom();
45-
}
46-
public Environment(DateTime initialDateTime, int randomSeed, TimeSpan? defaultStep = null)
47-
: base(initialDateTime, randomSeed, defaultStep) {
48-
Random = new SystemRandom(randomSeed);
49-
}
50-
}
51-
5224
/// <summary>
5325
/// Simulation hold the event queues, schedule and process events.
5426
/// </summary>
@@ -410,7 +382,7 @@ public TimeSpan RandExponential(TimeSpan mean) {
410382
/// <param name="mu">The mean of the normal distribution.</param>
411383
/// <param name="sigma">The standard deviation of the normal distribution.</param>
412384
/// <returns>A number that is normal distributed.</returns>
413-
public double RandNormal(IRandom random, double mu, double sigma) {
385+
public virtual double RandNormal(IRandom random, double mu, double sigma) {
414386
if (useSpareNormal) {
415387
useSpareNormal = false;
416388
return spareNormal * sigma + mu;
@@ -874,4 +846,43 @@ public override DateTime Peek() {
874846
}
875847
}
876848
}
849+
850+
/// <summary>
851+
/// Environments hold the event queues, schedule and process events.
852+
/// </summary>
853+
[Obsolete("Use class Simulation or ThreadSafeSimulation instead. Due to name clashes with System.Environment the class SimSharp.Environment is being outphased.")]
854+
public class Environment : ThreadSafeSimulation {
855+
public Environment()
856+
: base() {
857+
Random = new SystemRandom();
858+
}
859+
public Environment(TimeSpan? defaultStep)
860+
: base(defaultStep) {
861+
Random = new SystemRandom();
862+
}
863+
public Environment(int randomSeed, TimeSpan? defaultStep = null)
864+
: base(randomSeed, defaultStep) {
865+
Random = new SystemRandom(randomSeed);
866+
}
867+
public Environment(DateTime initialDateTime, TimeSpan? defaultStep = null)
868+
: base(initialDateTime, defaultStep) {
869+
Random = new SystemRandom();
870+
}
871+
public Environment(DateTime initialDateTime, int randomSeed, TimeSpan? defaultStep = null)
872+
: base(initialDateTime, randomSeed, defaultStep) {
873+
Random = new SystemRandom(randomSeed);
874+
}
875+
876+
protected static readonly double NormalMagicConst = 4 * Math.Exp(-0.5) / Math.Sqrt(2.0);
877+
public override double RandNormal(IRandom random, double mu, double sigma) {
878+
double z, zz, u1, u2;
879+
do {
880+
u1 = random.NextDouble();
881+
u2 = 1 - random.NextDouble();
882+
z = NormalMagicConst * (u1 - 0.5) / u2;
883+
zz = z * z / 4.0;
884+
} while (zz > -Math.Log(u2));
885+
return mu + z * sigma;
886+
}
887+
}
877888
}

SimSharp/Random/Pcg.cs

Lines changed: 1 addition & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -69,19 +69,7 @@ internal class Pcg {
6969
ulong _increment = 1442695040888963407ul;
7070
const ulong Multiplier = 6364136223846793005ul;
7171
const double ToDouble01 = 1.0 / 4294967296.0;
72-
73-
// This attribute ensures that every thread will get its own instance of PCG.
74-
// An alternative, since PCG supports streams, is to use a different stream per
75-
// thread.
76-
[ThreadStatic]
77-
static Pcg _defaultInstance;
78-
/// <summary>
79-
/// Default instance.
80-
/// </summary>
81-
public static Pcg Default {
82-
get { return _defaultInstance ?? (_defaultInstance = new Pcg(PcgSeed.GuidBasedSeed())); }
83-
}
84-
72+
8573
public int Next() {
8674
uint result = NextUInt();
8775
return (int)(result >> 1);

Tests/EnvironmentTests.cs

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -162,5 +162,18 @@ private IEnumerable<Event> ReproducibleProcess(Simulation env) {
162162
yield return env.TimeoutD(t3);
163163
env.ActiveProcess.Succeed(t1 + t2 + t3);
164164
}
165+
166+
[Fact]
167+
public void EnvironmentBackwardsCompat() {
168+
// make sure it returns the same normal-distributed random numbers as the 3.0.11 Environment
169+
#pragma warning disable CS0618 // Type or member is obsolete
170+
var env = new Environment(randomSeed: 10);
171+
#pragma warning restore CS0618 // Type or member is obsolete
172+
var rndNumbers = Enumerable.Range(0, 10).Select(x => env.RandNormal(0, 1)).ToArray();
173+
var old = new[] { 1.439249790053017, 0.539700657754765, -0.35962836744484883,
174+
0.37645276686883905, 0.037506631053281031, -0.92536789644140882, -0.87027850838312693,
175+
0.65864875161591829, 0.46713487767696055, -0.37878389025311837};
176+
Assert.Equal(old, rndNumbers);
177+
}
165178
}
166179
}

0 commit comments

Comments
 (0)