我想生成一百万位随机二进制文件但我的问题是代码需要花费很多时间而不执行为什么会发生这种情况?
string result1 = "";
Random rand = new Random();
for (int i = 0; i < 1000000; i++)
{
result1 += ((rand.Next() % 2 == 0) ? "0" : "1");
}
textBox1.Text = result1.ToString();
连接字符串是O(N)操作。字符串是不可变的,因此当您添加到字符串时,新值将被复制到新字符串中,这需要迭代前一个字符串。由于您为每次迭代添加了一个值,因此每次添加时必须读取的数量会增加,从而导致性能为O(N ^ 2)。由于您的N是1,000,000,这需要非常长的时间,并且可能正在吃掉存储这些中间丢弃字符串的所有内存。
构建具有任意数量输入的字符串时的常规解决方案是使用StringBuilder。虽然,一个1,000,000字符的位串仍然是笨重的。假设您想要/需要一个位串,您可以将代码更改为类似以下内容并具有更高性能的解决方案。
public string GetGiantBitString() {
var sb = new StringBuilder();
var rand = new Random();
for(var i = 0; i < 1_000_000; i++) {
sb.Append(rand.Next() % 2);
}
return sb.ToString();
}
这适用于我,我的盒子大约需要0.035秒:
private static IEnumerable<Byte> MillionBits()
{
var rand = new RNGCryptoServiceProvider();
//a million bits is 125,000 bytes, so
var bytes = new List<byte>(125000);
for (var i = 0; i < 125; ++i)
{
byte[] tempBytes = new byte[1000];
rand.GetBytes(tempBytes);
bytes.AddRange(tempBytes);
}
return bytes;
}
private static string BytesAsString(IEnumerable<Byte> bytes)
{
var buffer = new StringBuilder();
foreach (var byt in bytes)
{
buffer.Append(Convert.ToString(byt, 2).PadLeft(8, '0'));
}
return buffer.ToString();
}
然后:
var myStopWatch = new Stopwatch();
myStopWatch.Start();
var lotsOfBytes = MillionBits();
var bigString = BytesAsString(lotsOfBytes);
var len = bigString.Length;
var elapsed = myStopWatch.Elapsed;
len变量是一百万,字符串看起来像是1和0。
如果你真的想要填充你的文本框中的零和零,只需将其Text
属性设置为bigString
。