【发布时间】:2015-06-12 08:16:32
【问题描述】:
我注意到 MvxMessenger 订阅由于同一个 ViewModel 的多个实例而被多次调用。我读了一些关于取消订阅和处理令牌(这可以工作并防止多次调用)的内容,但我希望看到 ViewModel 被自然地垃圾收集,并且 Messenger 订阅也随之而来。
我想为 Android 设置一个类似于 https://github.com/slodge/MessengerHacking 的测试项目。所以这里有两个 ViewModel
public class FirstViewModel : MvxViewModel
{
private string _hello = "Hello MvvmCross";
public string Hello
{
get { return _hello; }
set { _hello = value; RaisePropertyChanged(() => Hello); }
}
private MvxCommand _showSecond;
public ICommand ShowSecond {
get {
_showSecond = _showSecond ?? new MvxCommand(() => ShowViewModel<SecondViewModel> ());
return _showSecond;
}
}
}
和
public class SecondViewModel : MvxViewModel
{
private readonly IMvxMessenger _messenger;
private readonly MvxSubscriptionToken _token;
public SecondViewModel(IMvxMessenger messenger) {
_messenger = messenger;
_token = _messenger.Subscribe<MyMessage> ((message) => {
Debug.WriteLine("incoming message");
});
}
private MvxCommand _send;
public ICommand Send {
get {
_send = _send ?? new MvxCommand(() => _messenger.Publish (new MyMessage (this)));
return _send;
}
}
private MvxCommand _garbageCollect;
public ICommand GarbageCollect {
get {
_garbageCollect = _garbageCollect ?? new MvxCommand(() => GC.Collect ());
return _garbageCollect;
}
}
}
然后我只有两个 MvxActivities 绑定到这些 ViewModel。如果我转到 SecondViewModel 并单击发送,我会看到订阅的事件触发一次。如果我在 FirstViewModel 和 SecondViewModel 之间来回切换,这些事件订阅会建立起来,然后单击 Send 会触发它们中的每一个。点击 GarbageCollect 似乎没有任何区别(我希望在点击后看到它只被调用一次)。
感觉好像当我单击 SecondViewModel 的后退按钮时,一旦 MvxActivity 被销毁,那么 SecondViewModel 应该有资格进行垃圾回收。
我注意到的另一件事是,即使我订阅而不将其保存到令牌中,行为也是一样的。我成功让事件停止触发的唯一方法是保存令牌并在令牌上调用 Unsubscribe 或 Dispose,但是在这种情况下感觉 SecondViewModel 仍然没有收集垃圾。
这可能与最近对 Xamarin.Android 的更改有关吗?或者有什么我没有得到的东西!
非常感谢
【问题讨论】: