Why not inherit from List<T>?

Why Not Inherit from List<T>

Using inheritance in programming can be powerful, but it's important to know when it's not the best choice. Specifically, inheriting from List<T> in languages like C# might seem convenient, but it can lead to several issues. Let’s explore why you might want to avoid this approach and consider better alternatives.

Potential Issues with Inheriting from List<T>

Unintended Behavior

When you inherit from List<T>, your new class automatically gains all the methods and properties of List<T>. While this might seem useful, it can lead to unexpected behavior if you override or extend these methods without fully understanding their implications.

Example:

public class CustomList<T> : List<T> { public void AddRange(IEnumerable<T> items) { // Custom logic before adding items base.AddRange(items); // Custom logic after adding items } }

In this example, overriding AddRange might interfere with how List<T> manages its internal state, potentially causing bugs that are hard to trace.

Violating the Liskov Substitution Principle

The Liskov Substitution Principle (LSP) is a fundamental concept in object-oriented design. It states that objects of a superclass should be replaceable with objects of a subclass without affecting the correctness of the program.

By inheriting from List<T>, you tightly couple your class to the specific behavior of List<T>. If List<T> changes in future updates, your subclass might break, violating LSP and making your code less robust.

Prefer Composition Over Inheritance

Instead of inheriting from List<T>, using composition is often a better choice. Composition involves building classes that contain instances of other classes, allowing for more flexible and maintainable code.

Benefits of Composition

  • Flexibility: You can change the behavior of your class without being tied to the implementation details of List<T>.
  • Encapsulation: You control which List<T> methods are exposed, preventing unintended usage.
  • Maintainability: Your class is less likely to break with updates to List<T> since you’re not directly inheriting from it.

Example:

public class CustomCollection<T> { private List<T> _items = new List<T>(); public void Add(T item) { // Custom logic before adding _items.Add(item); // Custom logic after adding } public IEnumerable<T> GetItems() { return _items.AsReadOnly(); } }

In this example, CustomCollection<T> uses a List<T> internally but only exposes the methods you want, allowing for better control and flexibility.

Trade-Offs Between Inheritance and Composition

Inheritance

Pros:

  • Simplicity: Easy to implement if there’s a clear "is-a" relationship.
  • Reusability: Directly reuse and extend functionalities of the base class.

Cons:

  • Tight Coupling: Changes in the base class can negatively impact the subclass.
  • Limited Flexibility: Harder to modify behavior without affecting the entire inheritance chain.

Composition

Pros:

  • Loose Coupling: Components can be changed or replaced without affecting other parts.
  • Enhanced Flexibility: Easier to combine different behaviors by composing objects.

Cons:

  • More Boilerplate: Requires more code to delegate methods and manage internal objects.
  • Complexity: Can introduce additional layers of abstraction, making the design slightly more complex.

When to Use Each Approach

Use Inheritance When:

  • There is a clear "is-a" relationship.
  • You need to extend or specialize the behavior of the base class.
  • The base class is designed to be extended (e.g., framework classes).

Use Composition When:

  • You want to build complex functionalities by combining simpler components.
  • There is a "has-a" relationship.
  • You need more flexibility and control over the exposed functionalities.

Additional Resources

Enhance your object-oriented design skills and prepare for interviews with these DesignGurus.io courses:

Helpful Blogs

Dive deeper into software design principles by visiting DesignGurus.io's blog:

By understanding when to use inheritance versus composition, you can create more flexible, maintainable, and efficient code. Happy coding!

TAGS
Coding Interview
CONTRIBUTOR
Design Gurus Team
-

GET YOUR FREE

Coding Questions Catalog

Design Gurus Newsletter - Latest from our Blog
Boost your coding skills with our essential coding questions catalog.
Take a step towards a better tech career now!
Explore Answers
What is the main language in Amazon?
What is a coding internship?
Who are the cloud service providers?
What is the youngest age to get an internship?
Why do I want to work for Stripe?
What questions should I ask Airbnb?
Related Courses
Grokking the Coding Interview: Patterns for Coding Questions course cover
Grokking the Coding Interview: Patterns for Coding Questions
The 24 essential patterns behind every coding interview question. Available in Java, Python, JavaScript, C++, C#, and Go. The most comprehensive coding interview course with 543 lessons. A smarter alternative to grinding LeetCode.
4.6
Discounted price for Your Region

$197

Grokking Modern AI Fundamentals course cover
Grokking Modern AI Fundamentals
Master the fundamentals of AI today to lead the tech revolution of tomorrow.
3.9
Discounted price for Your Region

$72

Grokking Data Structures & Algorithms for Coding Interviews course cover
Grokking Data Structures & Algorithms for Coding Interviews
Unlock Coding Interview Success: Dive Deep into Data Structures and Algorithms.
4
Discounted price for Your Region

$78

Design Gurus logo
One-Stop Portal For Tech Interviews.
Copyright © 2026 Design Gurus, LLC. All rights reserved.