2

在 VB.net 中,我有一个生成随机整数字符串的函数

Public Function RandomString(ByVal Size As Integer, ByVal LowerBound As Double, ByVal Upperbound As Double) As list (of integer)

它获取三个因素(大小、下界和上界)并生成一个长度为“大小”的随机列表,每个值在“下界”和“上界”之间随机

在顶部的代码中,我有:

Imports System.Random

函数的主体是这样的:

Dim rand As New Random
Dim mystr as new list (of integer)
for i as integer=1 to size
    mystr.add(rand.Next(Upperbound - LowerBound + 1) + LowerBound)
next
return mystr

在我的潜艇内,我有:

dim MyData(10) as list (of integer)
for i as integer = 0 to 9
    mydata(i) = new list (of integer)
    mydata(i) = RandomString(5,2,4)
next

奇怪的问题是,当我正常运行它时,它会生成 10 个完全相同的值的字符串。

例如像这样:

2,3,3,2,4
2,3,3,2,4
2,3,3,2,4
...

但是当我在循环内放置一个切换停止点(在我的子循环内循环)并逐步运行代码时,它可以正常工作并按预期生成不同的字符串。如

2,3,2,4,3
3,2,4,4,2
4,3,3,2,2
...

为什么会这样?我应该如何修改它以在正常运行中正常工作?

4

3 回答 3

2

当您创建一个 Random 实例时,如果您不传递您希望使用的种子,它将使用一个与时间相关的默认种子。从官方文档

默认种子值来自系统时钟并且具有有限的分辨率。因此,通过调用默认构造函数连续创建的不同 Random 对象将具有相同的默认种子值,因此将产生相同的随机数集。

这就是为什么您在调试时会得到“更随机”的结果 - 您在实例化之间留出了更多时间。

因此,要么为每个实例使用不同的种子,要么在每次实例化之间人为地给予更多时间(即:Thread.Sleep,但这是一个非常丑陋的 hack)。

于 2013-08-14T20:09:46.027 回答
1

@Renan 的回答是正确的。您还可以执行以下操作,它只初始化变量一次,但应该在多次调用期间为您提供唯一性。

Static rand As New Random
于 2013-08-14T20:24:37.987 回答
1

问题是,默认情况下,System.Random将根据当前时间自行播种。如果您在很短的时间内创建多个实例(例如循环),您将获得相同的种子,进而创建相同的序列。

您可以通过制作 Random 实例来避免这种情况Static

Public Function RandomString(ByVal Size As Integer, ByVal LowerBound As Double, ByVal Upperbound As Double) As List(of Integer)
    ' Static makes this instance get "preserved" across multiple calls to the method
    ' So it's only created once
    Static rand As New Random

    Dim mystr as new List(of Integer)
    For i as integer=1 to size
        mystr.add(rand.Next(Upperbound - LowerBound + 1) + LowerBound)
    next
    return mystr
End Function

这将导致在多个调用中使用相同的实例,这反过来又会导致它不使用相同的种子重新播种。但是请注意,如果您从多个线程中使用此方法,这将不是线程安全的。

于 2013-08-14T20:11:01.563 回答