大家好,我在我的 WP8 应用程序的 ScheduledAgent 中遇到内存泄漏问题。我正在尝试做的是循环更新应用程序的多个图 block ,这似乎没问题(关于内存使用),但由于某种原因,在更新图 block 后不会释放内存。
我的代码如下所示(内存使用情况由 Microsoft.Phone.Info.DeviceStatus.ApplicationCurrentMemoryUsage 测量):
protected override void OnInvoke(ScheduledTask task)
{
try
{
Deployment.Current.Dispatcher.BeginInvoke(() =>
{
// 5MB used
foreach (int id in myIdsList)
UpdateTile(id);
});
}
catch (Exception e)
{
if (Debugger.IsAttached)
Debugger.Break();
}
NotifyComplete();
}
更新方法如下所示:
public void UpdateTile(int id)
{
MyClass myClassInstance = GetInstanceById(id);
//~6MB used by now
Canvas drawingSurface = new Canvas();
//Add some Image objects to canvas (source to each image is a filePath
// contained in myClassInstance)
//~7MB
WriteableBitmap bigTileImage = new WriteableBitmap(691, 336);
bigTileImage.Render(drawingSurface, null);
bigTileImage.Invalidate();
//~9MB
var bigTilePath = string.Format(/*path here*/);
using (IsolatedStorageFile storage =
IsolatedStorageFile.GetUserStoreForApplication())
{
if (storage.FileExists(bigTilePath))
storage.DeleteFile(bigTilePath);
using (var isoFileStream = new IsolatedStorageFileStream(
bigTilePath, FileMode.Create, storage))
{
bigTileImage.SaveJpeg(isoFileStream, bigTileImage.PixelWidth,
bigTileImage.PixelHeight, 0, 100);
}
}
ShellTile tileToUpdate = ShellTile.ActiveTiles.FirstOrDefault(
x => x.NavigationUri.ToString().Contains("TileID="+id));
FlipTileData flipTileData = new FlipTileData()
{
//Set fields
WideBackgroundImage =
new Uri(("isostore:/"+bigTilePath, UriKind.Absolute),
};
tileToUpdate.Update(flipTileData);
//~10MB used
//Shouldn't memory be released by now??
// calling GC.Collect() has no effect
}
所以,这是一个 PeriodicTask,我的内存上限为 11MB,只要内存在迭代后没有释放,我就会得到 OutOfMemoryException。
也许我不了解基础知识,但我认为大部分占用的内存应该在将文件保存到 IS 后释放(或者每当 GC 决定收集时,但是,正如我所说,甚至显式调用 GC.Collect( )
没有效果)?
我做错了什么吗?有没有办法释放内存?
最佳答案
我不确定这是否是您内存泄漏问题的唯一原因,但是;您正在创建一个 tile 对象,并且 1) 您没有使用它 2) 您也没有释放它。
ShellTile tileToipdate = ShellTile.ActiveTiles.FirstOrDefault(x => x.NavigationUri.ToString().Contains("TileID="+id));
tileToipdate 对象的作用是什么?查询后您没有使用它。如果没用,就把它移除,看看它是否会做出任何改变。
如果你要使用这个对象,调用tileToipdate.Finalize()方法(在你完成它之后),它是mentioned在这里,引用“允许对象在对象被垃圾收集回收之前尝试释放资源并执行其他清理操作。(继承自 Object。)”
希望对您有所帮助。
关于c# - 计划代理内存泄漏,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15718025/