2017-04-21 121 views
2

如何检查某个类以任何方式实现通用接口?C#检查通用接口的实现

我有以下几点:

public class SomeQueryObject : IQueryObject<SomeQueryDto> 
{ 
    public SomeQueryDto query { get; set; } = new SomeQueryDto(); 
} 

public class SomeQueryDto : BaseQueryDto 
{ 
    // some properties 
} 

public class BaseQueryDto 
{ 
    // some properties 
} 


public interface IQueryObject<T> where T : BaseQueryDto 
{ 
    T query { get; set; } 
} 

是否有使用这个接口来检查参数实现,而无需提供T上的通用接口的方法吗? 传递基类的不匹配,并使用SomeQueryDto类会破坏点

private static string BuildQueryObjectString<T>(T dto) 
     where T : IQueryObject<?> 
{ 
    //use query field in method body 
    dto.query= foo; 
} 

我可以改变的接口来实现另一个非通用接口,并检查,但随后类可以只使用这个,而不是具有通用接口都:

public interface IQueryObject<T> : IQueryObject where T : BaseQueryDto 
{ 
    T query { get; set; } 
} 

public interface IQueryObject { } 

public class SomeQueryObject : IQueryObject 
{ 
    // no query field 
} 

private static string BuildQueryObjectString<T>(T dto) 
     where T : IQueryObject // kind of pointless, the above class would pass this check but doesn't implement the field 
{ 
    //method body, no access to query field 
    dto.query= foo; // error 
} 
+0

什么是IUDGroupQueryObject? – Scrobi

+0

我的不好,我是为了清晰而重新命名的东西,并错过了 – lanky393

回答

1

你有没有想是这样的:

​​

,但没有提供T1?

您可以根据您的需要简化它:以下是我认为您试图实现的完整代码示例。在AnotherClass中,您可以使用两种不同的方法签名。

public class BaseClass 
{ 
    public virtual string Str { get; set; } = "base"; 
} 

public class DerivedClass : BaseClass 
{ 
    public override string Str { get; set; } = "derived"; 
} 

public class TestingClass 
{ 
    public TestingClass() 
    { 
     AnotherClass a = new AnotherClass(); 

     Console.WriteLine(a.SomeMethod<GenericObjClass<BaseClass>, BaseClass>(new GenericObjClass<BaseClass>(){ Query = new BaseClass()})); 
     Console.WriteLine(a.SomeMethod<GenericObjClass<DerivedClass>, DerivedClass>(new GenericObjClass<DerivedClass>() { Query = new DerivedClass() })); 

     Console.WriteLine(a.SomeMethod(new GenericObjClass<BaseClass>() { Query = new BaseClass() })); 
     Console.WriteLine(a.SomeMethod(new GenericObjClass<BaseClass>() { Query = new DerivedClass() })); 
    } 
} 

public class AnotherClass 
{ 
    public string SomeMethod<T>(T obj) where T : IGenericObj<BaseClass> 
    { 
     return obj.Query.Str; 
    } 

    public string SomeMethod<T, T2>(T obj) where T : IGenericObj<T2> where T2 : BaseClass 
    { 
     return obj.Query.Str; 
    } 
} 

public class GenericObjClass<T> : IGenericObj<T> where T : BaseClass 
{ 
    public T Query { get; set; } 
} 


public interface IGenericObj<T> where T : BaseClass 
{ 
    T Query { get; set; } 
} 
+0

是的,这就是我想要的,说实话,我会解决通过这两个,就像你建议的,只是认为它可能更整洁:) – lanky393

0

如果我理解正确的,你,你要做的是检查类实现特别泛型类型通用接口。假设你有一个类的实例,你可以做,在这种方式:

class Dto 
{ 
    // definition 
} 

interface ISome<T> 
{ 
    // definition 
} 

class SomeDto: ISome<Dto> 
{ 
    // definition 
} 

... 
var instance = new SomeDto(); 

foreach(var type in instance.GetType().GetInterfaces()) { 
    if(type.IsGenericType 
     && type.GetGenericTypeDefinition() == typeof(ISome<>) 
     && type.GetGenericArguments()[0] == typeof(Dto)) { 
     // success 
    } 
} 

另外,如果您有任何情况,并希望使类检查,只需用typeof(SomeDto)取代instnace.GetType()

+0

我不想检查,我想有一个方法签名,可以采取任何类型的ISome <>。 谢谢 – lanky393

+0

所以我们来清除它:你有一个实现了'ISome '的类,并且想要在其中接受一个类型为'ISome '的参数的方法? – Seprum