Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/silverlight/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 动态控制内存泄漏_C#_.net_Winforms_Memory Leaks - Fatal编程技术网

C# 动态控制内存泄漏

C# 动态控制内存泄漏,c#,.net,winforms,memory-leaks,C#,.net,Winforms,Memory Leaks,我有一个Windows窗体应用程序。当我动态地向表单添加一些按钮,然后删除这些按钮时,就会出现内存泄漏 public partial class Form1 : Form { private Button[] buttons = new Button[1000]; private void button1_Click(object sender, EventArgs e) { for (int i = 0; i < 1000; i++)

我有一个Windows窗体应用程序。当我动态地向表单添加一些按钮,然后删除这些按钮时,就会出现内存泄漏

public partial class Form1 : Form
{
    private Button[] buttons = new Button[1000];

    private void button1_Click(object sender, EventArgs e)
    {
        for (int i = 0; i < 1000; i++)
        {
            var b = new Button();
            Controls.Add(b);
            buttons[i] = b;
        }

        for (int i = 0; i < 1000; i++)
        {
            Controls.Remove(buttons[i]);
            buttons[i].Dispose();
            buttons[i] = null;
        }
    }
}
公共部分类表单1:表单
{
私有按钮[]按钮=新按钮[1000];
私有无效按钮1\u单击(对象发送者,事件参数e)
{
对于(int i=0;i<1000;i++)
{
var b=新按钮();
增加(b);
按钮[i]=b;
}
对于(int i=0;i<1000;i++)
{
控件。移除(按钮[i]);
按钮[i].Dispose();
按钮[i]=null;
}
}
}
内存使用:

  • 加载表单后:3720KB
  • 单击按钮1后:5144 KB
(这些数字是在执行完全垃圾收集后记录的。程序在没有调试程序的情况下运行,发布版本。)


更奇怪的是,无论按钮单击执行多少次,内存使用量都保持在5100 KB左右。我做错了什么?

这不是内存泄漏。首先,如果您依赖Windows任务管理器来完成此任务,那是不对的。如果您真的想测量应用程序的实际内存,请尝试使用一些性能计数器。或者甚至像这样的事情

private Process currentProcess = System.Diagnostics.Process.GetCurrentProcess();
long totalBytesOfMemoryUsed = currentProcess.WorkingSet64;

其次,即使在堆中分配的对象是由垃圾收集器收集的,在它们被释放后,这并不意味着应用程序将释放未分配的内存。只有当操作系统为其他操作请求有线内存时,才会发生这种情况。底线是,这不是内存泄漏。

这不是内存泄漏。首先,如果您依赖Windows任务管理器来完成此任务,那是不对的。如果您真的想测量应用程序的实际内存,请尝试使用一些性能计数器。或者甚至像这样的事情

private Process currentProcess = System.Diagnostics.Process.GetCurrentProcess();
long totalBytesOfMemoryUsed = currentProcess.WorkingSet64;

其次,即使在堆中分配的对象是由垃圾收集器收集的,在它们被释放后,这并不意味着应用程序将释放未分配的内存。只有当操作系统为其他操作请求有线内存时,才会发生这种情况。底线是,这不是内存泄漏。

如果内存保持在5.1 mb,则没有内存泄漏。泄漏通常意味着它不会在某一点停止。您可以尝试校准
GC.Collect()
。此外,请尝试使用内存分析器,如。您从哪里获取使用次数?应用程序将保留内存,即使它当前未被使用,直到操作系统将其收回。由于您没有提到如何衡量内存使用情况,我想您只需查看任务管理器即可。对我来说,这是一种完全不现实的方法。取消运行内存探查器或至少一些性能计数器应该是一种方法。应用程序不会实时释放内存。如果操作系统保留一些额外的内存供将来使用,这对您的操作系统来说是很好的。当一个应用程序的内存使用量随着时间的推移而增长超过需要,并且当操作系统要求时无法释放额外的内存时,我们谈论内存泄漏。看看SQL Server,随着时间的推移,它会消耗掉所有可用内存,只有当windows请求另一个进程的可用内存时,它才会减少。这并不意味着你需要每天为你的服务器购买新的RAM…如果内存保持在5.1MB,那么就没有内存泄漏。泄漏通常意味着它不会在某一点停止。您可以尝试校准
GC.Collect()
。此外,请尝试使用内存分析器,如。您从哪里获取使用次数?应用程序将保留内存,即使它当前未被使用,直到操作系统将其收回。由于您没有提到如何衡量内存使用情况,我想您只需查看任务管理器即可。对我来说,这是一种完全不现实的方法。取消运行内存探查器或至少一些性能计数器应该是一种方法。应用程序不会实时释放内存。如果操作系统保留一些额外的内存供将来使用,这对您的操作系统来说是很好的。当一个应用程序的内存使用量随着时间的推移而增长超过需要,并且当操作系统要求时无法释放额外的内存时,我们谈论内存泄漏。看看SQL Server,随着时间的推移,它会消耗掉所有可用内存,只有当windows请求另一个进程的可用内存时,它才会减少。这并不意味着你需要每天为你的服务器购买新的RAM。。。