Cha*_*ell 5 vb.net asp.net string random
我已经构建了一个随机字符串生成器,但是我遇到了一个问题,如果我在Page_Load方法中多次调用该函数,该函数将返回相同的字符串两次.
这是代码
Public Class CustomStrings
''' <summary>'
''' Generates a Random String'
''' </summary>'
''' <param name="n">number of characters the method should generate</param>'
''' <param name="UseSpecial">should the method include special characters? IE: # ,$, !, etc.</param>'
''' <param name="SpecialOnly">should the method include only the special characters and excludes alpha numeric</param>'
''' <returns>a random string n characters long</returns>'
Public Function GenerateRandom(ByVal n As Integer, Optional ByVal UseSpecial As Boolean = True, Optional ByVal SpecialOnly As Boolean = False) As String
Dim chars As String() ' a character array to use when generating a random string'
Dim ichars As Integer = 74 'number of characters to use out of the chars string'
Dim schars As Integer = 0 ' number of characters to skip out of the characters string'
chars = { _
"A", "B", "C", "D", "E", "F", _
"G", "H", "I", "J", "K", "L", _
"M", "N", "O", "P", "Q", "R", _
"S", "T", "U", "V", "W", "X", _
"Y", "Z", "0", "1", "2", "3", _
"4", "5", "6", "7", "8", "9", _
"a", "b", "c", "d", "e", "f", _
"g", "h", "i", "j", "k", "l", _
"m", "n", "o", "p", "q", "r", _
"s", "t", "u", "v", "w", "x", _
"y", "z", "!", "@", "#", "$", _
"%", "^", "&", "*", "(", ")", _
"-", "+"}
If Not UseSpecial Then ichars = 62 ' only use the alpha numeric characters out of "char"'
If SpecialOnly Then schars = 62 : ichars = 74 ' skip the alpha numeric characters out of "char"'
Dim rnd As New Random()
Dim random As String = String.Empty
Dim i As Integer = 0
While i < n
random += chars(rnd.[Next](schars, ichars))
System.Math.Max(System.Threading.Interlocked.Increment(i), i - 1)
End While
rnd = Nothing
Return random
End Function
End Class
Run Code Online (Sandbox Code Playgroud)
但如果我打电话给这样的话
Dim rnd1 As New CustomStrings
Dim rnd2 As New CustomStrings
Dim str1 As String = rnd1.GenerateRandom(5)
Dim str2 As String = rnd2.GenerateRandom(5)
rnd1 = Nothing
rnd2 = Nothing
Run Code Online (Sandbox Code Playgroud)
响应将是这样的
g*3Jq
g*3Jq
我第二次打电话给它,它会
3QM0 $
3QM0 $
我错过了什么?我希望每个随机字符串都生成为唯一的.
这样做的原因是,当你构造一个Random类的实例时,它会从时钟中播种,但是如果你快速连续调用它,那么这个时钟的准确性不足以在每次调用时生成一个新的种子.
换句话说,这个:
Random r = new Random();
int i = r.Next(1000);
r = new Random();
int j = r.Next(1000);
Run Code Online (Sandbox Code Playgroud)
在i和中生成相同值的概率非常高j.
你需要做的是:
Random实例,以便它与每次调用使用的实例相同(但不幸的是,该类不是线程安全的,所以至少保留每个线程的缓存副本)这是一个示例程序,它为Random每个线程创建一个单独的实例,并从全局随机对象中播种这些实例.同样,这可能会产生可预测的序列.
using System;
using System.Collections.Generic;
using System.Threading.Tasks;
namespace SO2755146
{
public class Program
{
public static void Main()
{
List<Task> tasks = new List<Task>();
for (int index = 0; index < 1000; index++)
tasks.Add(Task.Factory.StartNew(() => Console.Out.WriteLine(RNG.Instance.Next(1000))));
Task.WaitAll(tasks.ToArray());
}
}
public static class RNG
{
private static Random _GlobalSeed = new Random();
private static object _GlobalSeedLock = new object();
[ThreadStatic]
private static Random _Instance;
public static Random Instance
{
get
{
if (_Instance == null)
{
lock (_GlobalSeedLock)
{
_Instance = new Random(_GlobalSeed.Next());
}
}
return _Instance;
}
}
}
}
Run Code Online (Sandbox Code Playgroud)
如果您只想从时钟中为每个随机实例播种,但至少每个线程生成随机序列,您可以像这样简化它:
using System;
using System.Collections.Generic;
using System.Threading.Tasks;
namespace SO2755146
{
public class Program
{
public static void Main()
{
List<Task> tasks = new List<Task>();
for (int index = 0; index < 1000; index++)
tasks.Add(Task.Factory.StartNew(() => Console.Out.WriteLine(RNG.Instance.Next(1000))));
Task.WaitAll(tasks.ToArray());
}
}
public static class RNG
{
[ThreadStatic]
private static Random _Instance;
public static Random Instance
{
get
{
if (_Instance == null)
_Instance = new Random();
return _Instance;
}
}
}
}
Run Code Online (Sandbox Code Playgroud)
这可能会使两个线程彼此非常接近地以相同的值播种,因此需要进行权衡.
| 归档时间: |
|
| 查看次数: |
2622 次 |
| 最近记录: |