【问题标题】:MonoTouch and IDisposable PatternMonoTouch 和 IDisposable 模式
【发布时间】:2011-10-08 13:38:54
【问题描述】:

阅读 MT 文档,我发现释放内存也可以实现 IDisposable .NET 模式。

例如,在扩展 UIViewController (MyViewController) 的自定义类中,我可以重写以下方法:

public override void Dispose (bool disposing)
{
   if (disposing){
     // do some stuff here
   }
   base.Dispose (disposing)
}

从这一点开始,我的两个问题是:

  1. 除了图片,我还需要发布哪些类型的元素?
  2. 是否必须从 MyViewController 类 (myViewController.Dispose()) 的实例调用 Dispose 方法,还是像 dealloc 方法一样自动调用 Dispose 方法?

提前谢谢你。问候。

【问题讨论】:

    标签: .net memory-management garbage-collection xamarin.ios idisposable


    【解决方案1】:

    IDisposable 的第一个 MonoTouch 用法与 Mono 或 .NET 相同。您在其他地方、stackoverflowMSDN... 上读到的关于此主题的内容都将适用于此处。

    对于 MonoTouch,重要的是要记住 NSObject 实现了 IDisposable,这很有意义,因为它代表了一个原生对象。这意味着从NSObject 继承的所有内容,monotouch.dll 的很大一部分,都实现了IDisposable

    1. 除了图片,我还需要发布哪些类型的元素?

    大多数托管基于NSObject的对象实例都很小,但它们可以表示大型本机对象(GC只会知道第一个,管理,大小)。

    所以最好尽可能处置基于 NSObject 的实例,例如当您将它们用作局部变量时。 using 模式使得在 C# 中很容易做到这一点。

    OTOH 根据您的判断,一个小的 NSString 不会占用太多内存,而其他的可能很大(或未知,例如 NSString GetWebPageContent (NSUrl)

    1. 是否必须从 MyViewController 类 (myViewController.Dispose()) 的实例调用 Dispose 方法,还是像 dealloc 方法一样自动调用 Dispose 方法?

    Dispose 模式的一部分确保 finalizer 将调用 Dispose(如果之前未调用过)。因此,GC 最终将回收与这些实例关联的内存(托管和非托管/本机)。

    您可能想要使用一些工具,例如Gendarme(将在 OSX 上运行)或 FxCop(仅限 Windows),如果您的某些类型具有未释放的 IDisposable 字段,它们将向您报告(例如)正确。

    免责声明:我是宪兵队的维护者 :-)

    【讨论】:

    • 感谢您的回复。非常有帮助。我唯一不明白的是:“大多数托管的基于 NSObject 的对象实例都很小,但它们可以表示大型的本地对象(GC 只会知道第一个托管的大小)。”你能解释一下这是什么意思吗?再次感谢您。
    • StackOverflow iDisposable Tag info 可以清楚地看出托管对象和非托管对象之间的区别:非托管对象超出了 .NET 垃圾收集器的范围。在 MT 中,我不太清楚两者之间的区别,而且我很难应用正确的内存管理行为。
    • new NSString ("a")new NSString ("aaa...1000...aaa") 这样的东西,从托管的角度来看,大小相同 - 即 sizeof(NSString) 主要只是一个句柄,IntPtr 指向本机 NSString 对象。因此,GC 无法使用 real 内存总量来决定何时收集。但是,一旦收集到第二个,Dispose 将被调用,并且长字符串将被释放。这就是在代码中使用(或不使用)Dispose 时的一些判断可以帮助您节省内存(通过确保尽快释放它)。
    • 这意味着如果直接处理 NS* 对象,我应该使用 using() 。但是,如果我使用内部使用 NS* 的托管 Monotouch 对象,这是否也适用?
    • monotouch.dll 的很大一部分是由工具 (btouch) 生成的,这样可以确保在需要时调用 Dispose(即您不必担心 MonoTouch 的内部结构)。然而,如果一个对象包含IDisposable 字段,那么实现IDisposable 本身是一个很好的候选(宪兵对此也发出警告)。关于何时以及如何使用这些类型的判断也适用(关于实现 IDisposable 并手动处理实例) - 但这样做绝不是 错误 (只要不再需要对象,任何地方!)
    猜你喜欢
    • 1970-01-01
    • 2017-03-14
    • 1970-01-01
    • 1970-01-01
    • 2010-12-10
    • 1970-01-01
    • 2018-04-09
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多