How to extend functions to Random class
-
20-04-2021 - |
Frage
I'm trying to extend the functions from a Random class.
public static class RandomExtensions
{
public static void NextEven(this Random rnd, int min, int max)
{
// ...
}
public static void ReseedRandomNumberGenerator(this Random rnd, int? seed = null)
{
rnd = seed.HasValue ? new Random(seed.Value) : new Random();
}
}
But my doubt is the second function ReseedRandomNumberGenerator. I need something where many classes can interacts a Random class, but all those classes should have the same instance.
Suposse that I invoke ReseedRandom... it's possible than the others classes should refresh or updated the new seed?
public class A()
{
protected Random Random = new Random();
}
public class B()
{
protected Random Random = new Random();
}
I know that this don't work. Maybe I need a static property, I'm not sure.
Lösung
You need to use the singleton pattern (See Implementing Singleton in C# on MSDN)
public class RandomSingleton
{
private static Random instance;
private RandomSingleton() {}
public static Random Instance
{
get
{
if (instance == null)
{
instance = new Randon();
}
return instance;
}
}
}
You can then access the same instance of Random in your code anywhere as follows:
RandomSingleton.Instance.NextInt(24);
Please note that there is no need to re-seed this Random
instance, because all your code will be using the same instance, hence you will not see repeated numbers.
Andere Tipps
The this
parameter is by-val, meaning: caller won't notice any reassignment you make to the value, hence your Reseed...
method doesn't do anything that the caller will notice. To do that it sounds like you want a static instance somewhere, but then you need to watch out for things like thread safety too.
Personally, I would create a separate API, such as :
public static class MyRandom {
static Random random = new Random();
static readonly object sync = new object();
public static void Seed(int seed) {
lock(sync) { random = new Random(seed); }
}
public static int Next() {
lock(sync) { return random.Next(); }
}
public static int Next(int max) {
lock(sync) { return random.Next(max); }
}
...
}
The use of lock
here prevents it all going unpredictable when being used by multiple threads; although at that point you can't guarantee a repeatable order anyway, but at least it won't explode in sparks.