我遇到了通过引用传递对象的问题。假设我有一个名为ViewModelBase
的对象,其定义如下:
public class ViewModelBase : IViewModelManager
{
public ViewModelBase()
{
}
// IViewModelManager implementation
}
然后,我定义另一个来自ViewModelBase
public class ExternalAssetViewModel : ViewModelBase
{
public ExternalAssetViewModel()
{
}
}
然后我创建了一个名为NotificationHandler
的静态类,它包含一个视图模型引用列表,因此一旦收到服务器通知,它就可以正确地更新视图模型:
public static class NotificationHandler
{
private static List<ViewModelBase> viewModelReferences = new List<ViewModelBase>();
public static void AddViewModelReference(ref ViewModelBase viewModel)
{
viewModelReferences.Add(viewModel);
}
}
现在,每次创建需要更新的新视图模型时,我都会将其添加到此静态列表中:
ExternalAssetViewModel viewModel = new ExternalAssetViewModel();
NotificationHandler.AddViewModelReference(ref viewModel);
但是,这会因以下编译错误而失败:
Argument 1: cannot convert from 'ref ExternalAssetViewModel' to 'ref ViewModelBase'
即使ExternalAssetViewModel
继承自ViewModelBase
,但技术上ExternalAssetViewModel
的类型为ViewModelBase
。通过更改AddViewModelReference
来获取泛型参数,然后为该参数定义约束,我能够解决这个问题:
public static void AddViewModelReference<T>(ref T viewModel) where T : ViewModelBase
{
viewModelReferences.Add(viewModel);
}
现在编译器又开心了。所以我的问题是,为什么代码最初会破坏?为什么编译器无法实现被引用的对象与定义的参数类型相同?
答案 0 :(得分:3)
您可能不需要ref
。
示例ref
不允许您的代码的原因:
void Method(ref MyBase v)
{
v = new MyBase();
}
MyDerived d = null;
Method(ref d);
如果允许,会将MyBase
分配给MyDerived
,类似于以下明显错误的代码:
MyDerived d = new MyBase();