C# WinForm应用程序降低系统内存占用方法总结

背景:

微软的 .NET FRAMEWORK 现在可谓如火如荼了。但是,.NET 一直所为人诟病的就是“胃口太大”,狂吃内存,虽然微软声称 GC 的功能和智能化都很高,但是内存的回收问题,一直存在困扰,尤其是 winform 程序,其主要原因是因为.NET程序在启动时,是需要由JIT动态编译并加载的,这个加载会把所有需要的资源都加载进来,很多资源是只有启动时才用的。

以XP 系统为例子,程序启动后,打开任务管理器,会看到占用的内存量比较大,你把程序最小化,会发现该程序占用的内存迅速减小到一个很小的值,再恢复你的程序,你会发现内存占用又上升了,但是比你刚启动时的内存占用值还是小的,这就是一个资源优化的过程,这个过程是操作系统主动完成的。

结论与展望:

创新设计大赛的项目已经快到交付的日期了,都说Winform占用内存大,于是想着看看自己写的基于手机邮件的远程关机软件(Mail_Based_Remote_Shutdown)占用内存情况,整个开发过程自己也在尽量写一些比较优美的代码来减少系统内存占用,今天看了下,刚打开时占用20M内存,然后一点点增加,最后到80多M,真是无法忍受,每次都是写了之后回过头来才发现自己的代码很丑,系统架构师的作用就体现出来了。

这里整理了一些网上关于Winform如何降低系统内存占用的资料,供参考:

1、使用性能测试工具dotTrace 3.0,它能够计算出你程序中那些代码占用内存较多
2、强制垃圾回收
3、多dispose,close
4、用timer,每几秒钟调用:SetProcessWorkingSetSize(Process.GetCurrentProcess().Handle, -1, -1);具体见附录。
5、发布的时候选择Release
6、注意代码编写时少产生垃圾,比如String + String就会产生大量的垃圾,可以用StringBuffer.Append
7、this.Dispose();    this.Dispose(True);   this.Close();    GC.Collect();  
8、注意变量的作用域,具体说某个变量如果只是临时使用就不要定义成成员变量。GC是根据关系网去回收资源的。
9、检测是否存在内存泄漏的情况,详情可参见:内存泄漏百度百科

附录:定期清理执行垃圾回收代码:

代码如下:

//在程序中用一个计时器,每隔几秒钟调用一次该函数,打开任务管理器,你会有惊奇的发现
 
#region 内存回收
[DllImport("kernel32.dll", EntryPoint = "SetProcessWorkingSetSize")]
public static extern int SetProcessWorkingSetSize(IntPtr process, int minSize, int maxSize);
/// <summary>
/// 释放内存
/// </summary>
public static void ClearMemory()
{
GC.Collect();
GC.WaitForPendingFinalizers();
if (Environment.OSVersion.Platform == PlatformID.Win32NT)
{
App.SetProcessWorkingSetSize(System.Diagnostics.Process.GetCurrentProcess().Handle, -1, -1);
}
}
#endregion

(0)

相关推荐

  • C#实现带消息数的App图标

    上次写了一篇博文,但是每次更新图标时,桌面会闪烁(刷新)http://www.jb51.net/article/73350.htm,有博友说人家的图标都不会刷新,还能动画.我想了一下,如果要达到这个效果,可以用Form来实现,就是在Form中嵌入一个图片,然后用一个label来动态显示消息数,关键是将Form的边框隐藏,背景设为透明即可.如果要有旋转或者缩放动画,都可以用C#来实现. using System; using System.Collections.Generic; using Sy

  • C# 禁止应用程序多次启动的实例

    通常我们的情况是,双击一个exe文件,就运行一个程序的实体,再双击一次这个exe文件,又运行这个应用程序的另一个实体.就拿QQ游戏来说吧,一台电脑上一般只能运行一个QQ游戏大厅(不过以前听说过有双开的外挂). 那我们的程序也能像QQ游戏那里禁止多次启动吗,答案是可以的,下面介绍下一个简单的实现方法,那就是Mutex(互斥). Mutex(mutual exclusion,互斥)是.Net Framework中提供跨多个线程同步访问的一个类.它非常类似了Monitor类,因为他们都只有一个线程能拥

  • c#取得控制台应用程序根目录

    1.取得控制台应用程序的根目录方法 方法1.Environment.CurrentDirectory 取得或设置当前工作目录的完整限定路径方法2.AppDomain.CurrentDomain.BaseDirectory 获取基目录,它由程序集冲突解决程序用来探测程序集 2.取得Web应用程序的根目录方法 方法1.HttpRuntime.AppDomainAppPath.ToString();//获取承载在当前应用程序域中的应用程序的应用程序目录的物理驱动器路径.用于App_Data中获取方法2

  • C#实现将应用程序设置为开机启动的方法

    本文实例讲述了C#实现将应用程序设置为开机启动的方法.分享给大家供大家参考.具体如下: private void WriteRegistry() { string strName = Application.ExecutablePath; if (File.Exists(strName)) { string strNewName = Path.GetFileName(strName); RegistryKey reg = Registry.LocalMachine.OpenSubKey("SOF

  • C#Web应用程序入门经典学习笔记之二

    读取Web.config中设置 Conn = new SqlConnection(ConfigurationSettings.AppSettings["cnFriends.ConnectString"]); <appSettings> <!--   User application and configured property settings go here.--> <!--   Example: <add key="settingNa

  • C#实现在应用程序间发送消息的方法示例

    本文实例讲述了C#实现在应用程序间发送消息的方法.分享给大家供大家参考,具体如下: 首先建立两个C#应用程序项目. 第一个项目包含一个Windows Form(Form1),在Form1上有一个Button和一个TextBox. 第二个项目包含一个Windows Form(Form1),在Form1上有两个Button,分别用来测试第一个应用程序中Button的Click事件和修改第一个应用程序中TextBox的值. 第一个应用程序中Form的代码如下: using System; using

  • C#Web应用程序入门经典学习笔记之一

    最近看了<Beginning C# Web Applications Wtith Visual Studio .Net >.感觉这本书在一些细节方面写的不错,特做笔记,为后来者提供一些或许有用的东东.今天先写出来一些,年前正确整理完. 当前日期: Lbll.Text = DateTime.Now.ToLongDataString(); This.controls.Add(lbl); URL: HyperLink reg = new HyperLink(); Reg.Text = "R

  • C#使用windows服务开启应用程序的方法

    本文实例讲述了C#使用windows服务开启应用程序的方法.分享给大家供大家参考.具体如下: 使用windows服务开启应用程序,会遇到如下问题 1.使用windows服务开启的应用程序不会显示应用程序界面 解决方法:当安装服务之后,选中服务,点击属性->登录,然后设置登录身份为本地系统账户,并允许服务与桌面进行交互 2.使用的是远程桌面进行查看,不会显示界面 解决方法:不能直接使用mstsc命令进入远程桌面,要使用mstsc /v:192.168.1.10 /admin命令 ,这里192.16

  • C#记录消息到日志文件的方法

    本文实例讲述了C#记录消息到日志文件的方法.分享给大家供大家参考.具体实现方法如下: public void LogMessageToFile(string msg) { System.IO.StreamWriter sw = System.IO.File.AppendText("log.txt"); try { string logLine = System.String.Format("{0:G}: {1}.", System.DateTime.Now, msg

  • C#向无窗口的进程发送消息

    注:本文适用.net2.0+的winform程序 一个winform程序,我希望它不能多开,那么在用户启动第二个实例的时候,作为第二个实例来说,大概可以有这么几种做法: 1.弹个窗告知用户[程序已运行]之类,用户点击弹窗后,退出自身 2.什么都不做,默默退出自身 3.让已运行的第一个实例把它的窗体显示出来,完了退出自身 显然第3种做法更地道,实现该效果的核心问题其实是:如何显示指定进程的窗口? 首先想到的是调用ShowWindow.SetForegroundWindow等API,配合使用可以将被

  • C#微信开发之接收 / 返回文本消息

    接收 / 返回文本消息 ①接收/返回文本消息原理说明 当普通微信用户向公众账号发消息时,微信服务器将POST消息的XML数据包到开发者填写的URL上,着手开发之前先行阅读微信公众平台接收普通消息微信开发文档,对微信的这种消息处理机制有一定了解之后再着手开发(微信开发接收普通消息开发文档) 注意点: 1.关于重试的消息排重,推荐使用msgid排重. 2.微信服务器在五秒内收不到响应会断掉连接,并且重新发起请求,总共重试三次.假如服务器无法保证在五秒内处理并回复,可以直接回复空串,微信服务器不会对此

随机推荐