Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Entity Framework 4, inheriting vs extending?

What are the advantages/disadvantages to each method?

I know I've read somewhere in either a book or on this site why using table inheritance is crappy for Entity Framework 4.

For instance, why not make one table which has an entityId, datecreated, datemodified and then have every other class inherit that in entity framework? Then my tables for all other entities don't need to have those columns. Then I can have a person class inherit that base class, and then a specific person inherit person.

I am not sure of the advantages of this though other than writing a smaller SQL script to generate the database...

Disadvantages I see are that it makes querying /viewing the data directly in SQL a big pain in the ass (all relevant information is broken across so many tables), and I also asked my friend who said:

"The biggest thing that sticks out for me is the fact that i wouldn't want my database to rely on the current inheritance structure of my application. if, for whatever reason, i wanted to change the design of my application in terms of inheritance, it wouldn't matter because my data wouldn't be reliant on my current system design. i think of data storage as just that--storage. the database is normalized according to proper database design, but inheritance is a programatic choice of application development, not data storage. that alone would prevent me from using it. inheritance is a very difficult thing to do properly when it comes to designing an application. it's much easier to change application code than it is to change and migrate database data when most less-seasoned devs approach a problem they approach it with inheritance. i did too when i first started developing. it logically makes sense. however once developing for a long time you learn that delegation is really the best way to go (services calling services in the case of soa) and that single-purpose services provide a lot more reuse than inheritance."

Which also makes sense to me.

So

1) In general, what are the pros/cons of inheritance vs extending
2) In my specific example above, what would be more appropriate?
3) If my example is crappy for either or both, what is a good example for using inheritance and for using extending?

I've used both before but as I am far from seasoned, I am still unsure how to handle all situations.

10 Votes, 8 favorited, over a hundred views and no one can expand? =(.

like image 803
SventoryMang Avatar asked Nov 08 '10 18:11

SventoryMang


People also ask

How does Entity Framework handle inheritance?

By default, EF maps the inheritance using the table-per-hierarchy (TPH) pattern. TPH uses a single table to store the data for all types in the hierarchy, and a discriminator column is used to identify which type each row represents.

Which class do we inherit from while interacting with Entity Framework?

TPH is the default inheritance pattern in the Entity Framework, so all you have to do is create a Person class, change the Instructor and Student classes to derive from Person , add the new class to the DbContext , and create a migration.

Which of the following inheritance hierarchy is support in EF core?

TPH is the only inheritance pattern that the Entity Framework Core supports.


2 Answers

I'm a little late to the party, but I've been having the same questions as you regarding inheritance in EF and found a pretty good summary for you to read. It's an excerpt from Julie Lerman's book Programming Entity Framework.

After reading it, here's my conclusions on the topic:

1) In general, what are the pros/cons of inheritance vs extending - The pros really depend on the table strategy you choose. See How to choose an Inheritance Strategy - MSDN Blog. However, they are only "pros" on the assumption that you have already decided to use inheritance at all. And that is not a decision to take lightly.

The cons are many, but the biggest is the inability to add an existing entity into the database as a derived entity. For example: I have a Student which inherits from Person. There is a Person record for John Smith. Some time later I need John Smith to be a Student. Well too bad. That's not possible. (At least not without circumventing EF with a stored procedure).

2) In my specific example above, what would be more appropriate? - In your example you should just add those columns (entityId, datecreated, datemodified) to tables that need them. You could use a Complex Type for datecreated and datemodified, but that wouldn't be necessary unless you're a very strict DRY guy. Even then, it might be overkill. The reason is that once you have an entity, you can never add that entity to another derived table. A Person (which is a BaseEntity) can not be added as a Student later. Also, writing LINQ queries would be far more complex than needed. Alex already showed that.

3) If my example is crappy for either or both, what is a good example for using inheritance and for using extending? - Generally, if you can make your base-type abstract, inheritance might work for you. But you should still consider other options first. If your base type will be directly instantiated somewhere, just use composition. Inheritance gets very troublesome when it comes to actually querying and inserting records.

In summary, just because you can do inheritance in EF does not mean you should. If you can get away with an inheritance-free design, then by all means do it.

like image 157
Aaron Avatar answered Nov 09 '22 15:11

Aaron


I have tried similar thing as you describe, and the main problem I see, is that u can't create ObjectSet<T> for derived type. So you will not have ObjectSet<Person> repository. If you derive all your Entities from for example BusinessObject entity, you will be able to work only with ObjectSet<BusinessObject>. If you want to query only Person repository, you can write query like Context.BusinessObjectSet.OfType<Person>().ToList() but i think it will not generate proper SQL under the hood and will first get full BusinessObject rows and then filter out Person entities in memory. So I guess it will have huge performance impact.

like image 45
Alex Burtsev Avatar answered Nov 09 '22 15:11

Alex Burtsev