iva*_*lee 3 c# random static constructor
我有两个班,一个教师班和一个班级班.在我的程序中,我创建了一个包含10个Teacher对象的数组,每个Teacher对象中有一个包含10个Student对象的数组.每个Student对象也有一个整数数组作为成员变量,当每个Student被实例化时,它自己的整数数组都用随机数生成器中的数字填充.我的程序是这样的:
这是我遇到的问题:似乎每次为每个教师创建10个Student对象时,即使我调用.Next()函数直到下一个,Student对象构造函数中的随机数生成器也不会重置或更改为下一个Teacher对象创建10个Student对象.我想要的是10个教师对象,每个对象都有自己的学生对象,这些对象有自己的整数数组,里面填充了随机生成的数字.
任何帮助,将不胜感激!在我的最后一个问题中,我遇到了构造函数的这种问题,这是一个问题是否是静态的,我不确定这次是什么情况.如果我对任何事情都不够清楚,请问我问题!
更新**所以在查看MSDN后,我在他们的示例代码"Thread.Sleep(2000)"中找到并将其粘贴到我的学生构造函数中,只是为了看看它做了什么.它似乎已经解决了问题,虽然我的程序现在运行得慢很多,是否有一个最小的睡眠值要等到Random.Next()使用来自时钟的新种子,即使我确实解决了问题,是否有更好的方法吗?我的随机数生成器已经是Student的静态成员变量.
如果在短时间内Random使用默认构造函数初始化多个实例Random(),则可能会导致它们最终具有相同的种子值(这取决于时间),因此每次都会生成相同的随机序列.
您可以通过初始化单个静态Random实例并在所有Student实例之间共享它来解决此问题.只要您不是多线程,这是非常安全的.
public class Student
{
private static readonly Random random = new Random();
}
Run Code Online (Sandbox Code Playgroud)
从Random()构造函数的MSDN页面:
默认种子值源自系统时钟并具有有限的分辨率.因此,
Random通过调用默认构造函数紧密连续创建的不同对象将具有相同的默认种子值,因此将生成相同的随机数集.通过使用单个Random对象生成所有随机数可以避免此问题.您还可以通过修改系统时钟返回的种子值然后显式地将此新种子值提供给Random(Int32)构造函数来解决此问题.有关更多信息,请参阅Random(Int32)构造函数.
编辑:虽然您声明您的随机数生成器已经是静态成员,但如果您在每次Student初始化期间重复(冗余地)实例化它,这仍然是不够的.以下代码仍然不正确:
public class Student
{
private static Random random;
private int[] numbers;
public Student()
{
random = new Random();
numbers = new int[10];
for (int i = 0; i < 10; ++i)
numbers[i] = random.Next();
}
}
Run Code Online (Sandbox Code Playgroud)
您需要将其替换为仅实例化Random一次的版本,如下所示:
public class Student
{
private static readonly Random random = new Random();
private int[] numbers;
public Student()
{
numbers = new int[10];
for (int i = 0; i < 10; ++i)
numbers[i] = random.Next();
}
}
Run Code Online (Sandbox Code Playgroud)
常见的缺陷Random是每次需要随机值时都要创建一个新实例.
for (int i = 0; i < 1000; i++) {
var random = new Random();
list.Add(random.Next());
}
Run Code Online (Sandbox Code Playgroud)
这不能按预期工作,因为Random使用实际时间来创建第一个随机值.但是,时钟的分辨率有限.可能是几个连续的迭代返回相同的时间,因此返回相同的(伪)随机值!
解决方案是random只创建一次.
var random = new Random();
for (int i = 0; i < 1000; i++) {
list.Add(random.Next());
}
Run Code Online (Sandbox Code Playgroud)
您还可以声明random为静态类成员
public static readonly Random RandomGenerator = new Random();
Run Code Online (Sandbox Code Playgroud)