开发者

C#: Non-Generic classes using generic classes undefined

I have a Generic Interface

public interface TheInterface<T> where T : IObject

I also have an object class that this interface works with

public class SomeObject : IObject

I then have a class that implements the interface

public class ClassThatWorksWithSomeObject : TheInterface<SomeObject>

This all works well enough. Later on I add a class that works with TheInterface class independent 开发者_StackOverflow中文版of what version of IObject he uses.

public class IDoStuffToInterface
{
    public IDoStuffToInterface(TheInterface<IObject> interface)
    {
         //bla bla
    }
}

Problem is I can't pass ClassThatWorksWithSomeObject in there, even if It inherits from the intreface and it's generic object inherits from IObject.

I guess there are some cases that it could be hurtful if it did, but I can't think of any.

Is there a way to do this better?


I don't know the detail impelmentation, you can try:

public interface TheInterface<out T> where T : IObject 

if you are using C#4.0


I think what you're doing should work, but you may need to use the covariance and contravariance keywords.


You need to make you definition of TheInterface covariant so that it accepts the wider types of IObject:

public interface TheInterface<out T> where T : IObject


You should be able to do this in C#4.0 by marking the interface type as contravariant, but I think you can also get around this by making the IDoStuffInterface generic as well.

public class IDoStuffToInterface<T> where T : IObject
{
    public IDoStuffToInterface(TheInterface<T> interface)
    {
         //bla bla
    }
}

Since SomeObject qualifies for T and ClassThatWorksWithSomeObject implements TheInterface<SomeObject>, it should be acceptable as a parameter.


The other way I saw mentioned by tvanfosson was to make your IDoStuffToInterface class generic. That would work nicely as well, if (as it appears in the example) the TheInterface is being passed into the constructor and (presumably) stored in the class.

However, if it were just a function (or even a constructor) that uses the TheInterface and it isn't being stored in the class, it would probably be better to make the function itself generic and leave the class alone. For example:

public class IDoStuffToInterface
{
    public void DoSomething<T>(TheInterface<T> theInterface) where T : IObject
    {
        //bla bla
    }
}

This would allow you to do the following:

ClassThatWorksWithSomeObject myObject = new ClassThatWorksWithSomeObject();
IDoStuffToInterface actor = new IDoStuffToInterface();
actor.DoSomething(myObject);

That compiles without any problem because the compiler is able to tell by inference that you are actually calling

actor.DoSomething<SomeObject>(myObject);

Now, I think that using covariance is still probably the best option if you are in control of the interface definition. But I wanted to add this as another option for when you don't have that degree of control in your interface.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜