1

我正在尝试制定一些通用接口,其中包括 Dictionary 及其包含的项目,这两者目前看起来都像下面的代码。

正如你所看到的,我在 Dictionary 上进行了下注,使值成为对象。理想情况下,我想要一个具有 TParentMOdel 的协变 KEY 和 TModel 的协变值的接口,就像项目一样,但到目前为止我还不能解决这个问题(也不确定它是否可能)。

在我尝试在下面的最后一个使用示例中添加最后一项之前,我所做的似乎有效。GenderVm 本质上是一个 ISatteliteVm

似乎问题在于 Gender 是一个枚举,这对我来说并不完全有意义。本例中的 TParentModel 是 Person,它是 Party 的子类。协方差似乎在这里起作用,因为我可以添加其他项目,其中 TParentModel 是一个人。

这就是为什么我说问题似乎在于价值性别。它是一个枚举,虽然枚举是一个对象,但我认为类型约束系统不支持枚举。

有没有简单的解决方法,比如演员表?A 有人看到设计 SatelliteMap 的更好方法吗?

干杯,
贝里尔

物品

public interface ISatelliteVm<out TParentModel, out TModel> : ISatelliteVm
{
    TParentModel ParentModel { get; }
    TModel Model { get; }
}

字典

public class SatelliteVmMap<TParentModel> : Dictionary<Type, ISatelliteVm<TParentModel, object>>, IEditableObject, IIsDirty
{

    public void Add(ISatelliteVm<TParentModel, object> item) {
        if (item == null)
            throw new ArgumentNullException("item");
        Add(item.GetType(), item);
    }
}

用法(包含 SatelliteMap 的抽象类)

public interface IHubViewModel<out TModel> where TModel : Entity
{

    public void AddSatelliteVm(ISatelliteVm<TModel, object> vm) {
        if (_satelliteVmMap == null) {
            _satelliteVmMap = new SatelliteVmMap<TModel>();
        }
        if (_satelliteVmMap.ContainsKey(vm)) return;

         _satelliteVmMap.Add(vm);
    }
}

用法(包含多个 ISatelliteVm 条目的子类)

    public abstract class PartyDetailVm : HubViewModel<Party>
{
    ...

    public LifespanVm LifespanVm { get { return GetSatelliteVm<LifespanVm>(); } }
    public AvatarVm AvatarVm { get { return GetSatelliteVm<AvatarVm>(); } }
    public TelecomNumberPcmShellVm TelecomNumberPcmShellVm { get { return GetSatelliteVm<TelecomNumberPcmShellVm>(); } }

    ...
}

用法(包含多个 ISatelliteVm 条目的子类)

public class PersonDetailVm : PartyDetailVm
{
    ...

    public PersonNameVm PersonNameVm { get { return GetSatelliteVm<PersonNameVm>(); } }
    public HonorificVm HonorificVm { get { return GetSatelliteVm<HonorificVm>(); } }

    // THIS is the problem child I cannot add to the map
   ** public GenderVm GenderVm { get { return GetSatelliteVm<GenderVm>(); } } **

 }

错误

错误 82 参数 1:无法从“Parties.Presentation.ViewModels.PimDetailVms.PersonDetailVms.GenderVm”转换为“Core.Presentation.Wpf.ViewModels.MasterDetailVms.DetailVms.SatelliteVms.ISatelliteVm”

为比利编辑

比利,SatelliteVm 只是一个实现 ISatelliteVm 的基类。Person 是 Party 的子类,Gender 是枚举。

public class GenderVm : SatelliteViewModel<Person, Gender>
{
}

对 GenderVm 的更改似乎可以解决问题(不知道为什么!)

 public class GenderVm : SatelliteViewModel<Person, Gender>, ISatelliteVm<Party, object>
{

    Party ISatelliteVm<Party, object>.ParentModel { get { return base.ParentModel; } }

    object ISatelliteVm<Party, object>.Model { get { return base.Model; } }
}
4

1 回答 1

2

请参阅文档

泛型接口的变化仅支持引用类型。值类型不支持方差。例如,IEnumerable<int>不能隐式转换为IEnumerable<object>,因为整数是由值类型表示的。

这必须解决您的问题。

也许你应该改变Gender成为一个班级?

于 2012-09-30T17:41:16.483 回答