WinForm C#"新流程"在无限循环中导致应用程序崩溃

时间:2016-03-01 22:15:52

标签: c# winforms

我有一个要求,我需要我的代码块无限运行(退出是基于按钮点击的中断)。

在每次迭代中,我创建一个Process,启动它,操作输出然后处理Process。

    void status()
    {
        do{
            Process test1 = new Process();
            test1.StartInfo.FileName = "doSomething"; // doSomething is executable
            test1.StartInfo.UseShellExecute = false;
            test1.StartInfo.CreateNoWindow = true;
            test1.StartInfo.RedirectStandardOutput = true;
            test1.StartInfo.RedirectStandardError = true;
            test1.Start();
            string output = test1.StandardOutput.ReadToEnd();
            test1.WaitForExit();
            if (Regex.IsMatch(output, "DEVICE_READY", RegexOptions.IgnoreCase))
            {
                pictureBox2.BackColor = Color.Green;
            }
            else
            {
                pictureBox2.BackColor = Color.Yellow;
            }
            test1.Dispose();        
        }while(true);    
    }

问题是应用程序崩溃了这段代码。如果我只是删除循环,它工作正常。

我在调试时检查,应用程序的内存使用量随着循环的每次迭代而不断增加,使应用程序崩溃在一个点上。

我理解的是Dispose()将释放所有资源......所以每次迭代都不应该增加内存。

有人可以帮助了解导致内存使用量增加的原因吗?

1 个答案:

答案 0 :(得分:0)

当我必须处理饥饿的进程(例如图片处理)时,我所做的就是明确地调用垃圾收集器。

这不是最干净的方式(花费很多),但合理使用,它就可以解决问题。

void status()
{
    // will be used to explicitly call the garbage collector
    const int COLLECT_EVERY_X_ITERATION = 10;

    // store the current loop number
    int currentIterationCount = 0;

    do
    {
        // increase current iteration count
        currentIterationCount++;

        using (Process test1 = new Process())
        {
            test1.StartInfo.FileName = "doSomething"; // doSomething is executable
            test1.StartInfo.UseShellExecute = false;
            test1.StartInfo.CreateNoWindow = true;
            test1.StartInfo.RedirectStandardOutput = true;
            test1.StartInfo.RedirectStandardError = true;
            test1.Start();
            string output = test1.StandardOutput.ReadToEnd();
            test1.WaitForExit();
            if (Regex.IsMatch(output, "DEVICE_READY", RegexOptions.IgnoreCase))
            {
                pictureBox2.BackColor = Color.Green;
            }
            else
            {
                pictureBox2.BackColor = Color.Yellow;
            }
        }

        // Explicitly call garbage collection every 10 iterations
        if (currentIterationCount % COLLECT_EVERY_X_ITERATION == 0)
            GC.Collect(GC.MaxGeneration, GCCollectionMode.Forced);
    } while (true);
}