Прежде всего, никогда не делайте этого:
if (animal.GetType() == typeof(Fish))
Почему бы и нет? Потому что, если animal
является Goldfish
, производным типом Fish
? GetType
вернет typeof(Goldfish)
. Вместо этого всегда делайте это:
if (animal is Fish fish)
, потому что это верно, независимо от того, animal
равен Fish
или Goldfish
или Shark
.
Во-вторых, ваш код предполагает, что все, что не является фантастическим, является млекопитающим, но я думаю, что птицы, ящерицы и ракообразные хотели бы с вами не согласиться. Ваш код не является надежным перед лицом неожиданных входных данных.
Реальный вопрос, на который нужно ответить, это , почему формальный параметр типа object
в первую очередь ? Это похоже на проблему, чтобы решить. Если эта проблема не решаема, сделайте все возможное, чтобы исправить ее:
Uri HandleFish(Fish fish) ...
Uri HandleMammal(Mammal mammal) ...
Uri HandleAnimal(Animal animal)
{
if (x is Fish fish) return HandleFish(fish);
if (x is Mammal mammal) return HandleMammal(mammal);
...
return HandleOther(x);
}
Uri HandleOther(object x) ...
Uri HandleObject(object x)
{
if (x is Animal animal) return HandleAnimal(animal);
...
return HandleOther(x);
}
Теперь, по крайней мере, вы работаете с системой типов.
Или в более новых версиях C# вы Можно сказать,
switch(x)
{
case Fish fish: return HandleFish(fish);
...
Альтернативный подход заключается в том, чтобы поместить logi c в саму иерархию типов.
class Animal
{
public virtual Uri Handle() ...
}
class Fish : Animal
{
public override Uri Handle() ...
}
А теперь, если x
равно Animal
, тогда вы просто return ((Animal)x).Handle());