当计时器打开时,内存堆积,导致内存泄漏 [英] As the timer is on, the memory is getting piled up leading to memory leak

查看:87
本文介绍了当计时器打开时,内存堆积,导致内存泄漏的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我没有在我的代码中使用任何GDI对象来处理导致托管内存泄漏的问题。

附上我的代码,任何人都可以告诉我为什么内存堆积如山。



I am not using any GDI objects in my code to dispose that leads to managed memory leak.
Attaching my code, can anyone tell me why that memory is getting piled up.

namespace SampleTemplate
{
    public partial class SelectTemplate : Form
    {
        public SelectTemplate()
        {
            InitializeComponent();
        }

        private void SelectTemplate_Load(object sender, EventArgs e)
        {   
            //
            // Set the Timer interval
            //
            this.forwardTimer.Interval = 3000;

            //
            // Count the number of Images in the Folder specified
            //
            try
            {
                string dir = "C:\\SignatureTemplates";
                files = Directory.GetFiles(dir, "*.jpg");

                numberOfImages = files.Length;
                backwardCount = numberOfImages;

                //
                // Load the first Image in to the picturebox
                //
                if (0 != currentCount)
                {
                    image = Image.FromFile(files[currentCount]);
                } // if
                else
                {
                    image = Image.FromFile(files[0]);
                } // else
                this.pictureBox1.Image = image;
                this.pictureBox1.SizeMode = PictureBoxSizeMode.Normal;

                //
                // Display the count of the Template
                //
                this.countLabel.Text = (currentCount + 1) + "/" + numberOfImages;
            } // try
            catch (Exception)
            {
                MessageBox.Show("Exception caught");
            }
            finally
            {
                if (0 == numberOfImages)
                {
                    this.Close();
                }
            } // finally

            //this.pauseBtn.Enabled = false;

        } // SelectTemplate_Load

        private void pauseBtn_Click(object sender, EventArgs e)
        {
            //
            // Stop the timer 
            //
            this.forwardTimer.Stop();
            playFlag = false;
        }

        private void playBtn_Click(object sender, EventArgs e)
        {
            //
            // Start the timer 
            //
            this.forwardTimer.Start();
            playFlag = true;
        }

        private void forwardTimer_Tick(object sender, EventArgs e)
        {
            //
            // operation to be performed after the specified time elapses.
            //
            if (currentCount < numberOfImages - 1)
            {
                this.pictureBox1.Image = Image.FromFile(files[currentCount + 1]);
                currentCount++;
                this.countLabel.Text = (currentCount + 1) + "/" + numberOfImages;
            } // if
            else if (numberOfImages - 1 == currentCount )
            {
                currentCount = 0;
                this.pictureBox1.Image = Image.FromFile(files[currentCount]);
                this.countLabel.Text = (currentCount + 1) + "/" + numberOfImages;
            } // else if
        }

推荐答案

之前

Before
this.pictureBox1.Image = Image.FromFile(files[currentCount]);
this.pictureBox1.Image = Image.FromFile(files[currentCount + 1]);



你需要这样做:


You Need to Do this :

if(this.pictureBox1.Image  != null)
{
this.pictureBox1.Image.Dispose();
this.pictureBox1.Image  = null;
}



您需要在计时器勾选中分配新图像之前处理旧图像。



也适用于:


you need to dispose the old image before assign new image in your timer tick.

Also For :

this.countLabel.Text = (currentCount + 1) + "/" + numberOfImages;



你最好这样做:


you better make it this way :

this.countLabel.Text = string.Format("{0}/{1}",(currentCount + 1) ,numberOfImages);



导致使用+ with strings将创建新的字符串以联系



编辑:

这是我在你发布的代码上发现的唯一漏洞,如果你没有合适的工具,内存泄漏是棘手的,很难捕获。



开始时不要使用Windows任务管理器来检测泄漏,因为它不准确而是使用Memory Profiler程序来帮助你。



这里有一些有用的链接可以帮助您进行搜索:



如何检测并避免内存和资源泄漏在.NET应用程序中 [ ^ ]



垃圾收集器基础知识和性能提示 [ ^ ]



如何以编程方式在.NET中测量当前进程的总内存消耗量? [ ^ ]



8 C#开发人员犯的最常见错误
[ ^ ]


cause using + with strings will create new string to contact

Edit :
well this is the only leaks I can find on your posted code, memory leaks is tricky and hard to catch if you don't have the right tools.

For start don't use Windows Task Manager to detect leaks because it's not accurate instead use Memory Profiler program to help you.

Here some useful links to help you with your search :

How to detect and avoid memory and resources leaks in .NET applications[^]

Garbage Collector Basics and Performance Hints[^]

How to measure the total memory consumption of the current process programatically in .NET?[^]

8 Most common mistakes C# developers make
[^]


而不是创建一个一开始就是文件名数组,为什么不创建一个图像数组。然后你只需要分配正确的图像。无需文件IO,处置或内存分配。
Instead of creating an array of filenames at the start, why not create an array of images. Then you just need to assign the correct image. No file IO, Disposing, or memory allocation require.


这篇关于当计时器打开时,内存堆积,导致内存泄漏的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆