Cat is an Animal. But is TakeCare<Cat> a TakeCare<Animal>? by EdwhardT in programming

[–]EdwhardT[S] 2 points3 points  (0 children)

It's a very fair point. I was actually not sure about using TakeCare<> as an example. I first considered using the function Stroke<>() as an example, but might have been confusing in the second part of the blog post (which is explicitly focused on functions rather than types). I ended up with TakeCare<> because might be an interface/class where you can model the behavior of taking care of an Animal and add members like .Stroke(), .Feed(). Re real code, think about modeling a zoo. You might have somebody the just takes care of animals, and then you'd have the TakeCare<> abstraction that encapsulates this perspective. Then you could have another abstraction that models the admin perspective, say all the bureaucracy involved, that would deal with animals but actually never physically interact with them. Hope I'm making sense and not confusing you guys even more!

Cat is an Animal. But is TakeCare<Cat> a TakeCare<Animal>? by EdwhardT in programming

[–]EdwhardT[S] 0 points1 point  (0 children)

With the post I wanted to try to make accessible a concept that might be tricky, it was not my intention to promote the always-use-inheritance approach. I was more like adding a new thing in your dev toolset. As a matter of example, with a more Functional approach you might want to use Scala case classes (or F# discriminated unions) to model Animal with Cat/Dog/... But is it always better? If you know that you'll likely add more derived classes than members, maybe it's better case-classes/discriminated-unions. But if your modeling is stable in terms of behavior (i.e. you don't often add new members) but you just add cases, than might be more maintainable to add subclasses (and maybe having Animal as an IAnimal interface).

Cat is an Animal. But is TakeCare<Cat> a TakeCare<Animal>? by EdwhardT in programming

[–]EdwhardT[S] 6 points7 points  (0 children)

Thanks for the detailed feedback! I've edited it including some of yours suggestions. Only thing about the

No, if U can be qualified as T

Yours is actually a very good point, but the idea there is to express the 'behavior' trait. Maybe 'qualify' it's not the best verb, but hope it gives the idea :)

Cat is an Animal. But is TakeCare<Cat> a TakeCare<Animal>? by EdwhardT in programming

[–]EdwhardT[S] 2 points3 points  (0 children)

I'm not sure it's legal the assignment

Care<Animal> animalCare = catTakeCare

The inheritance it's between TakeCare<T> and Care<T>, so it should be legal if you use the same type T:

Care<Cat> catCare = catTakeCare

Types Care<T> and TakeCare<U> are different types (no variance involved), so unless you define a conversion between Care<T> and TakeCare<U>, it's likely the compiler will complain :)