推断通用接口类型

时间:2014-04-07 16:57:01

标签: c# .net generics interface

- 上下文

我有以下5个对象

IChangeStatus<T>
myFirstClass : IChangeStatus<firstClassEnum>
mySecondClass : IChangeStatus<secondClassEnum>

myClassHandler<TEntity>
myFirstClassHandler : myClassHandler<myFirstClass>

出于问题的目的,我们可以假设接口只有属性

T Status { get; }

- 问题

1.-如何在myClassHandler中的方法中询问TEntity实例是否实现了IChangeStatus

2.-如何假设特定的IChangeStatus迭代IEnumerable TEntity

3 个答案:

答案 0 :(得分:2)

要检查您的类是否实现了IChangeStatus,您只需执行以下操作:

public void FooMethod(ClassType myClass)
{
  var doesImplementIChange = myClass as IChangeStatus<SomeClass>
  if (doesImplementIChange != null)
  {
    // Do stuff..
  }
}

迭代你的类的IEnumerable:

foreach (var data in myClass.OfType<MyType>())
        {
            // Do stuff..
        }

或者,你可以这样做:

foreach (var cls in myClass)
        {
            var myCls = myClass as IChangeStatus<SomeClass>;
            if (myCls != null)
            {
                // Do stuff..
            }
        }

答案 1 :(得分:2)

如果您想在T中使用IChangeStatus<T>中的MyClassHandler,则必须添加其他类型参数。例如:

class MyClassHandler<TEntity, TStatus>
    where TEntity : IChangeStatus<TStatus>
{
     public IEnumerable<TStatus> Statuses
     {
          get { return _entities.Select(entity => entity.Status); }
     }
}

where子句将确保实体和状态类型相关。

如果您不想这样做,您可以添加一个额外的非通用接口,该接口公开Status类型的Object属性。你会失去一些静态类型,但你不需要额外的类型参数。

答案 2 :(得分:0)

我发现了另一个SO Question - Check if a type implements a generic interface without considering the generic type arguments,它给了我一个更通用的答案,这就是我所寻找的:

return entity.GetType().GetInterfaces()
       .Where(i => i.IsGenericType)
       .Any(i => i.GetGenericTypeDefinition() == typeof(IChangeStatus<>));

关于IEnumerable的迭代,假设IChangeStatus的特定类型,因为我们得到了指向,然后类型确实实现了接口因此具有Status属性...所以我去了dynamic类型。< / p>