C# .NET Core应用使用Google Sheets API后内存占用居高不下问题咨询
内存占用过高核心原因
- 重复创建用户控件未正确销毁:每次切换页面都新建
StokKayitlari实例,若旧实例未从父容器移除、也未调用Dispose方法释放,GC无法回收该实例及其持有的所有数据对象,内存会持续累加。 - 全局大对象引用未释放:你将存储2万行数据的
IList<IList<Object>>声明为类全局字段,用完后未主动置空,只要控件实例不被回收,这份全量数据就会一直占用内存。 - 数据存储冗余:你额外在内存中存储了一份全量的接口返回数据,和DataTable中的数据重复占用内存,完全没有必要。
优化方案
- 优先修改页面切换逻辑:每个类型的用户控件仅创建1次,切换页面时仅做显示/隐藏操作,无需重复创建实例、重复加载数据,从根源避免重复内存占用。
- 若需要每次打开页面都刷新数据,切换页面时必须销毁旧控件:先将旧控件实例从父容器的
Controls集合中移除,再调用Dispose()方法释放控件资源,最后将持有控件的变量置为null,确保GC可以正常回收对象。 - 优化当前页面代码:将全量数据集合从类全局字段改为Load方法内的局部变量,方法执行完成后会自动释放引用,无需等待控件回收。
- 提前清空旧数据:每次加载新数据前,先清空两个DataTable的旧行数据,避免旧数据残留占用内存。
- 重写控件的Dispose方法:主动释放DataTable等资源,确保控件销毁时所有大对象引用都被清除。
优化后代码示例
public partial class StokKayitlari : UserControl { private async void StokKayitlari_Load(object sender, EventArgs e) { this.Enabled = false; // 加载前先清空历史数据 StokKayitlariTable.Rows.Clear(); KritikSayidakilerTable.Rows.Clear(); try { // 改为局部变量,方法执行完自动释放引用 IList<IList<Object>> stokKayitlariListe = await Form1.requests.StokKayitlariniAl(); foreach (IList<Object> stokKaydi in stokKayitlariListe) { StokKayitlariTable.Rows.Add(stokKaydi[0], stokKaydi[2], stokKaydi[1], stokKaydi[4], stokKaydi[3], stokKaydi[5], stokKaydi[7]); // 替换Parse为TryParse避免格式错误抛出异常 if (int.TryParse(stokKaydi[3]?.ToString(), out int stokMiktari) && int.TryParse(stokKaydi[6]?.ToString(), out int kritikMiktar) && stokMiktari <= kritikMiktar) { KritikSayidakilerTable.Rows.Add(stokKaydi[0], stokKaydi[2], stokKaydi[1], stokKaydi[3]); } } KritikSayidakilerTable.ClearSelection(); this.Enabled = true; } catch { this.Enabled = true; MessageBox.Show("Stok kayıtları yüklenirken bir hata oluştu. Lütfen bağlantınızı kontrol edip tekrar deneyin !", "Hata !", MessageBoxButtons.OK, MessageBoxIcon.Error); return; } } // 重写Dispose方法主动释放资源 protected override void Dispose(bool disposing) { if (disposing) { StokKayitlariTable?.Dispose(); KritikSayidakilerTable?.Dispose(); } base.Dispose(disposing); } }
如果优化后仍存在内存持续上涨的情况,可以通过Visual Studio自带的内存诊断工具,查看堆中是否存在多个StokKayitlari实例,定位持有实例引用的源头即可解决问题。
内容的提问来源于stack exchange,提问作者Ertugrul
相关产品推荐
相关产品推荐

