【问题标题】:Faster way to generate random text file C#生成随机文本文件 C# 的更快方法
【发布时间】:2018-11-11 21:21:13
【问题描述】:

输出应该是一个大文本文件,其中每一行的形式为 Number.String,文本是随机的:

347. Bus
20175. Yes Yes
15. The same
2. Hello world
178. Tree

文件大小必须以字节为单位。有兴趣以最快的方式生成大约 1000MB 及以上的文件。

有我生成随机文本的代码:

public string[] GetRandomTextWithIndexes(int size)
    {
        var result = new string[size];

        var sw = Stopwatch.StartNew();
        var indexes = Enumerable.Range(0, size).AsParallel().OrderBy(g => GenerateRandomNumber(0, 5)).ToList();
        sw.Stop();
        Console.WriteLine("Queue fill: " + sw.Elapsed);

        sw = Stopwatch.StartNew();
        Parallel.For(0, size, i =>
        {
            var text = GetRandomText(GenerateRandomNumber(1, 20));
            result[i] = $"{indexes[i]}. {text}";
        });

        sw.Stop();
        Console.WriteLine("Text fill: " + sw.Elapsed);

        return result;
    }

public string GetRandomText(int size)
    {
        var builder = new StringBuilder();

        for (var i = 0; i < size; i++)
        {
            var character = LegalCharacters[GenerateRandomNumber(0, LegalCharacters.Length)];
            builder.Append(character);
        }

        return builder.ToString();
    }

private int GenerateRandomNumber(int min, int max)
    {
        lock (_synlock)
        {
            if (_random == null)
                _random = new Random();
            return _random.Next(min, max);
        }
    }

我不知道如何使这段代码不使用字符串大小而是使用 MB 大小。当我将大小设置为大约 1000000000 时,我收到OutOfMemoryException。也许有一些更快的方法来生成索引

【问题讨论】:

  • 我建议您随时写入文件,而不是将整个内容构建为内存中的字符串。更快地到达 OutOfMemoryException 似乎只能解决部分问题。
  • 除非您是编写慢速代码的专家,否则要输出到文件的数据的实际生成与将数据写入文件所需的时间相比将相形见绌。我不会太担心“优化”生成部分。哦,你不应该在内存中生成整个文件,你应该在生成数据时打开流写入器并写入它。操作系统非常擅长代表您处理缓冲区和缓存。
  • 生成一种拉链炸弹会更快吗?
  • 你能放完整的例外吗

标签: c# arrays file generator


【解决方案1】:
  1. 磁盘是您的瓶颈,无需并行处理
  2. 在写入之前无需将所有内容都存储在内存中

using (var fs = File.OpenWrite(@"c:\w\test.txt"))
using (var w = new StreamWriter(fs))
{
    for (var i = 0; i < size; i++)
    {
        var text = GetRandomText(GenerateRandomNumber(1, 20));
        var number = GenerateRandomNumber(0, 5);
        var line = $"{number}. {text}";
        w.WriteLine(line);
    }
}

【讨论】:

    【解决方案2】:

    最好将完整的例外放在问题中。我敢打赌它显示在

    var result = new string[size];
    

    1000000000 对于字符串数组的大小太大了,尝试运行这个dotnetfiddle,你会得到:

    运行时异常(第 12 行):超出支持的数组尺寸 范围。 堆栈跟踪: [System.OutOfMemoryException:超出支持的数组尺寸 范围。] 在 Program.Main() :第 12 行

    请查看以下内容以了解您收到该异常的原因以及解决方法。

    What is the Maximum Size that an Array can hold?

    Can't create huge arrays

    Error when Dictionary count is bigger as 89478457

    【讨论】:

      猜你喜欢
      • 2023-03-22
      • 1970-01-01
      • 2010-10-26
      • 2023-02-01
      • 2022-10-04
      • 1970-01-01
      • 2012-11-12
      • 1970-01-01
      • 2012-10-17
      相关资源
      最近更新 更多