我正在维护WPF应用程序。我在项目中添加了UWP nedia播放器。但是,内存使用率太高。我意识到UWP媒体播放器已经做到了,所以我创建了可重复的代码。
while (true)
{
var mp = new MediaPlayer()
{
Source = MediaSource.CreateFromUri(new Uri("Test.mp4"))
};
Thread.Sleep(1000);
mp.Play();
Thread.Sleep(1000);
mp.Dispose();
}
此代码发生内存泄漏。我创建了MediaPlayer并将其丢弃!但是,它的内存使用量会无限增长。
如何在此代码上捕获内存泄漏?
这是.NET Core 3.0项目。 (带有WPF的XAML孤岛)我还没有测试它是否发生在纯UWP项目中。
有人说这很自然,因为这是一个循环。但是,下面的代码不会造成任何内存泄漏,因为GC有效。 (当然,不会收集某些(但有限制的)引用。)
while (true)
{
new SomeClass();
}
答案 0 :(得分:1)
代码写入内存的方式会膨胀并不断增长,直到内存用完为止。我也在纯UWP中进行了验证。如果进行以下两项更改,您会发现内存将保持稳定,并且每次循环后系统将回收所有内存:
这是未显示任何泄漏的代码(在UWP中经过测试)。在WPF中,Dispatcher调用看起来会稍有不同:
private async void PlayMedia()
{
var ms = MediaSource.CreateFromUri(new Uri("ms-appx:///Media1.mp4"));
var mp = new MediaPlayer()
{
Source = ms
};
Thread.Sleep(1000);
mp.Play();
Thread.Sleep(1000);
mp.Dispose();
ms.Dispose();
await Dispatcher.RunAsync(CoreDispatcherPriority.Normal, new DispatchedHandler(PlayMedia));
}
作为旁注:如果SomeClass是纯托管代码类,则您提到的“ SomeClass”比较并不是完全一样,因为您在此处创建的对象是复杂的本机Windows运行时对象,周围只有一个薄的托管代码包装器。
现在也在WPF中进行了测试:我重现了原始的内存增长问题,然后应用了建议的更改并验证了内存不再增长。这是我的测试项目以供参考:https://1drv.ms/u/s!AovTwKUMywTNuLk9p3frvE-U37saSw
我也将WPF应用程序打包为Windows应用程序包运行your shared solution,但在最新发布的Windows 10版本(17763.316)上没有泄漏。下面是运行解决方案一段时间后的内存诊断屏幕截图。如果这是特定于您正在运行的内部人员构建的,请通过反馈中心记录错误。我认为在这一点上,我们应该按照回答结束这个问题。
答案 1 :(得分:0)
这绝对是Windows 10 19H1的错误。因为内置应用程序(电影和电视)具有相同的内存泄漏问题。要重现此内容,只需重复该打开的视频文件并关闭它即可。