【转】C#中的Random.Next()方法一直返回0
昨天网站被人DOS攻击,网站的同时连接数达到了1000多,我的程序是一个投票的程序,在投票之前需要做验证码认证,不过验证码是放在Cookie中的,这给了作弊者一个可乘之机。在作弊者发动大规模作弊攻击时,网站的验证码出现了很奇怪的现象,总是返回AAAA,也就是说Random.Next(int number)方法总是返回0了。这是怎么回事呢?
通过google查出Random确有这个毛病,原因是Random本身是非线程安全的,而在Asp.net中是多线程环境,Random.Next方法在多线程环境下跑到一定时候,就会出现这种情况。
可以参考这篇blog:http://blogs.msdn.com/brada/archive/2003/08/14/50226.aspx
他推荐使用RandomNumberGenerator类,我当时情急之中,直接使用了Guid.NewGuid().ToString(0,4)了。或者通过下面的类,编程线程安全的调用Random类的Next方法。
{
private static Random random = new Random();
public static int Next()
{
lock (random)
{
return random.Next();
}
}
}
style="FONT-SIZE: 10pt; FONT-FAMILY: Arial">This question came up on an internal
list recently… Thought I’d share it with you… "urn:schemas-microsoft-com:office:office" />
style="FONT-SIZE: 10pt; FONT-FAMILY: Arial">
style="FONT-SIZE: 10pt; FONT-FAMILY: Arial">Q: We have created a System.Random
object and shared it among multithreads.
After calling m_random.Next() for awhile (eg. 1 day), it stops generate
any random but only return zero. I realize that random is not thread safe. style="mso-spacerun: yes"> I interpreted it as it might return the
same random (in race condition) not that it will only return zero after
sometime.
style="FONT-SIZE: 10pt; FONT-FAMILY: Arial">
style="FONT-SIZE: 10pt; FONT-FAMILY: Arial">A: This comes up now and then. style="mso-spacerun: yes"> As you note, and as we say in the docs,
the class is not threadsafe. That
means anything can happen. In this
case it looks like the seed is getting corrupted. style="mso-spacerun: yes"> Consider this fix:
style="FONT-SIZE: 10pt; FONT-FAMILY: 'Courier New'; mso-bidi-font-family: Arial">
style="MARGIN: 0in 0in 0pt; mso-pagination: none; mso-layout-grid-align: none"> style="FONT-SIZE: 10pt; COLOR: black; FONT-FAMILY: 'Courier New'; mso-bidi-font-family: Verdana">class
ThreadSafeRandom
style="MARGIN: 0in 0in 0pt; mso-pagination: none; mso-layout-grid-align: none"> style="FONT-SIZE: 10pt; COLOR: black; FONT-FAMILY: 'Courier New'; mso-bidi-font-family: Verdana">{
style="MARGIN: 0in 0in 0pt; mso-pagination: none; mso-layout-grid-align: none"> style="FONT-SIZE: 10pt; COLOR: black; FONT-FAMILY: 'Courier New'; mso-bidi-font-family: Verdana"> style="mso-tab-count: 1"> private static Random random
= new Random();
style="MARGIN: 0in 0in 0pt; mso-pagination: none; mso-layout-grid-align: none"> style="FONT-SIZE: 10pt; COLOR: black; FONT-FAMILY: 'Courier New'; mso-bidi-font-family: Verdana">
style="MARGIN: 0in 0in 0pt; mso-pagination: none; mso-layout-grid-align: none"> style="FONT-SIZE: 10pt; COLOR: black; FONT-FAMILY: 'Courier New'; mso-bidi-font-family: Verdana"> style="mso-tab-count: 1"> public static int
Next()
style="MARGIN: 0in 0in 0pt; mso-pagination: none; mso-layout-grid-align: none"> style="FONT-SIZE: 10pt; COLOR: black; FONT-FAMILY: 'Courier New'; mso-bidi-font-family: Verdana"> style="mso-tab-count: 1"> {
style="MARGIN: 0in 0in 0pt; mso-pagination: none; mso-layout-grid-align: none"> style="FONT-SIZE: 10pt; COLOR: black; FONT-FAMILY: 'Courier New'; mso-bidi-font-family: Verdana"> style="mso-tab-count: 2"> lock
(random)
style="MARGIN: 0in 0in 0pt; mso-pagination: none; mso-layout-grid-align: none"> style="FONT-SIZE: 10pt; COLOR: black; FONT-FAMILY: 'Courier New'; mso-bidi-font-family: Verdana"> style="mso-tab-count: 2">
{
style="MARGIN: 0in 0in 0pt; mso-pagination: none; mso-layout-grid-align: none"> style="FONT-SIZE: 10pt; COLOR: black; FONT-FAMILY: 'Courier New'; mso-bidi-font-family: Verdana"> style="mso-tab-count: 3">
return random.Next();
style="MARGIN: 0in 0in 0pt; mso-pagination: none; mso-layout-grid-align: none"> style="FONT-SIZE: 10pt; COLOR: black; FONT-FAMILY: 'Courier New'; mso-bidi-font-family: Verdana"> style="mso-tab-count: 2">
}
style="MARGIN: 0in 0in 0pt; mso-pagination: none; mso-layout-grid-align: none"> style="FONT-SIZE: 10pt; COLOR: black; FONT-FAMILY: 'Courier New'; mso-bidi-font-family: Verdana"> style="mso-tab-count: 1"> }
style="MARGIN: 0in 0in 0pt; mso-pagination: none; mso-layout-grid-align: none"> style="FONT-SIZE: 10pt; COLOR: black; FONT-FAMILY: 'Courier New'; mso-bidi-font-family: Verdana">}
style="FONT-SIZE: 10pt; FONT-FAMILY: Arial">
style="FONT-SIZE: 10pt; FONT-FAMILY: Arial">Also, if you are using this for any
kind of security\privacy purposes, we suggest using the Random number generator
in the System.Security namespace: <a
href="http://msdn.microsoft.com/library/en-us/cpref/html/frlrfSystemSecurityCryptographyRandomNumberGeneratorClassTopic.asp">RandomNumberGenerator.

浙公网安备 33010602011771号