简体   繁体   中英

C# Type casting base class / interface vs. generic method

Say I have a simple inheritance structure with a shared interface:

public interface IMammal
{
  ...
}

public class Human : IMammal
{
  ...
}

public class Animal : IMammal
{
  ...
}

And say in a different class (Main.cs or whatever), I want to implement a method. Which of the following is the "best practice":

public void MyFunction(IMammal input)
{
   // Do cool things with the IMammal.
}

Or

public void MyFunction<T>(T input) where T : IMammal
{
   // Do the same cool things with the IMammal.
}

Note: A possible solution in this simple case would be to make IMammal an abstract class and implement MyFunction in that abstract class. I need to keep the IMammal an interface though.

The best practice would usually to be the first case, and let the polymorphic behaviour of the underlying runtime handle types for you. Unless you specifically need to know the type (and as a generic!) it's best not to pass that around.

the case for the second option comes in when you're going to be making calls to other methods which need to be generic, such as those manipulating collections or serialization, and which must deal with T instead of the actual type of the object. This however is very rare and very specific behaviour, so it's better to use it only as absolutely necessary.

It depends on what MyFunction does . If MyFunction works just as designed without generics then leave it that way - using polymorphism is generally cleaner that introducing generics. If you get to a point where using generics is beneficial (eg like adding to a List<T> rather than a List<Mammal> then switch to generics.

Create code that works , then focus on making it better .

I think it's better the first one, I mean than if you are calling other class you should pass the interface instead a class.

public void MyFunction(Mammal input)
{
   // Do cool things with the mammal.
}

Also it's better to cal interface IMammal instead Mammal.

That's because MyFunction is a method of another class, according to best practices it's better to inject an Interface instead an object.

In your particular case, I would in general opt in for the first option.

However, for more complex scenarios, 2nd option is better because it allows you to further specify the type constraints, such as inheriting from multiple interfaces, or a class and an interface etc. It will also for example allow you to instantiate new T objects, if you also include new() in the method's where clause.

I see two implementations are equivalent. Then simple be the best, so option #1 I prefer.

If MyFunction is a behavior of Mammal, it should be in the interface. If you do some validation eg and requires something else from a higher layer for ex, put it in other class should be nice.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM