.NET Object Relationships
On this page
Understanding the relationships between objects is fundamental to building robust and maintainable .NET applications. These relationships define how classes interact and depend on each other.
Association
Association represents a relationship between two classes where one class knows about another. This is the most general form of relationship and can be one-to-one, one-to-many, many-to-one, or many-to-many.
In .NET, association is typically implemented through fields or properties that hold references to objects of other types.
Example: One-to-Many Association
A Department
can have many Employee
objects.
public class Employee
{
public int EmployeeId { get; set; }
public string Name { get; set; }
}
public class Department
{
public string DepartmentName { get; set; }
public List<Employee> Employees { get; set; } = new List<Employee>();
public void AddEmployee(Employee employee)
{
Employees.Add(employee);
}
}
Aggregation
Aggregation is a specialized form of association where one class (the whole) contains or is composed of other classes (the parts). However, the parts can exist independently of the whole.
Think of a Car
and its Engine
. The engine can exist on its own, but it's part of the car.
Example: Aggregation
public class Engine
{
public string Type { get; set; }
}
public class Car
{
public string Model { get; set; }
public Engine Engine { get; set; } // Aggregation: Engine is part of Car, but could exist independently
public Car(Engine engine)
{
Engine = engine;
}
}
Composition
Composition is a stronger form of aggregation. Here, the part cannot exist independently of the whole. If the whole is destroyed, the parts are also destroyed.
Consider a Room
and its Furniture
. If the room is demolished, the furniture within it is also gone.
Example: Composition
public class Furniture
{
public string Item { get; set; }
}
public class Room
{
public string RoomName { get; set; }
private List<Furniture> _furnitureItems = new List<Furniture>();
public Room(string roomName)
{
RoomName = roomName;
}
public void AddFurniture(Furniture item)
{
_furnitureItems.Add(item);
}
// When Room is disposed, the furniture is effectively gone with it in this model.
}
Inheritance
Inheritance models an "is-a" relationship. A derived class (child) inherits properties and methods from a base class (parent). This promotes code reuse and establishes a hierarchy.
In C#, inheritance is achieved using the colon syntax (:
).
Example: Inheritance
public class Vehicle
{
public virtual void Drive()
{
Console.WriteLine("Driving the vehicle...");
}
}
public class Car : Vehicle // Car "is a" Vehicle
{
public override void Drive()
{
Console.WriteLine("Driving the car...");
}
}
public class Motorcycle : Vehicle // Motorcycle "is a" Vehicle
{
public override void Drive()
{
Console.WriteLine("Riding the motorcycle...");
}
}
For more details on Inheritance, see the Inheritance documentation.
Dependency
Dependency occurs when a class uses another class in some way, typically as a parameter in a method, a local variable, or a static method call. The dependent class doesn't own or directly contain the dependency.
A class that sends an email depends on an email service.
Example: Dependency
public interface IEmailService
{
void SendEmail(string to, string subject, string body);
}
public class NotificationService
{
private readonly IEmailService _emailService;
// Dependency injected via constructor
public NotificationService(IEmailService emailService)
{
_emailService = emailService;
}
public void SendWelcomeEmail(string userEmail)
{
_emailService.SendEmail(userEmail, "Welcome!", "Thank you for joining!");
}
}
Key Takeaways
- Association: General "uses-a" relationship.
- Aggregation: "has-a" where parts can be independent.
- Composition: Stronger "has-a" where parts depend on the whole.
- Inheritance: "is-a" relationship for code reuse and hierarchy.
- Dependency: Using another class without ownership (e.g., via parameters).