This pattern represents part-whole hierarchies of objects such that the consumers or the clients can treat the objects and also the compositions of objects in a uniform manner Design patterns are tested, proven solutions to recurring problems that are often encountered in software designs. When used judiciously, they can help you to solve complex design problems easily. The GOF (Gang of Four) design patterns are categorized as Creational, Structural, or Behavioral. The Composite design pattern falls under the Structural category and helps you to implement a composite structure of objects such that the clients can treat the objects and also the compositions in a uniform manner. What is the Composite design pattern all about? The Composite design pattern enables you to compose one whole object from one or more individual objects to represent a part-whole hierarchy. As an example, we can build a tree (a composite structure) using multiple objects (also called the leaves of the tree). In essence, the Composite design pattern enables you to isolate an abstraction from the actual implementation. The participants The participants in the Composite design pattern include the following: Component — This is represented by either an abstract class or an interface and serves as the base type for all objects in the hierarchy CompositeElement — This is represented using a concrete class that defines the necessary operations that can be performed on the child components, i.e., Add, Remove, Get, Find, etc. methods. Leaf — This represents a leaf component, and is defined using a class that doesn’t have any subclass Consider the following class, named Employee. This is an abstract class and represents the “Component” in this design. It contains abstract methods to add, an employee, remove an employee and also get data related to one or more employees. public abstract class Employee { protected string name; protected double salary; public Employee(string name, double salary) { this.name = name; this.salary = salary; } public abstract void Add(Employee employee); public abstract void Remove(Employee employee); public abstract string GetData(); } The abstract class Employee also contains an argument constructor to assign values to the name and salary variables. The next class in our design is named “TeamLead,” and it represents the “Composite” type in our design, extends the Employee class, and provides the definition for the abstract methods. public class TeamLead : Employee { List<Employee> lstEmployee = new List<Employee>(); public TeamLead(string name, double salary) : base(name, salary) { } public override void Add(Employee employee) { lstEmployee.Add(employee); } public override void Remove(Employee employee) { lstEmployee.Remove(employee); } public override string GetData() { StringBuilder sbEmployee = new StringBuilder(); foreach (Employee emp in lstEmployee) { sbEmployee.Append(emp.GetData()+ "n"); } return sbEmployee.ToString(); } } The last class in our design is the TeamMember class that represents the leaf node in the composite structure. Here’s how this class looks: public class TeamMember : Employee { public TeamMember(string name, double salary) : base(name, salary) { } public override void Add(Employee employee) { //Operation not permitted since this is a leaf node. } public override void Remove(Employee employee) { //Operation not permitted since this is a leaf node. } public override string GetData() { return "Name: "+ name + "tSalary: "+salary.ToString("N2"); } } A leaf node in a composite structure doesn’t have any children, right? Note that since the TeamMember class represents a leaf node in the composite structure, there are no implementations of the “Add” or the “Remove” methods in this class. The following code snippet illustrates how you can create instances of the Employee class, add them to the employee’s collection and then display the data in the console window. static void Main(string[] args) { Employee employeeA = new TeamMember("Joydip Kanjilal", 20000); Employee employeeB = new TeamMember("Samuel Jones", 45000); Employee teamLead = new TeamLead("Steve Smith", 75000); teamLead.Add(employeeA); teamLead.Add(employeeB); Console.WriteLine(teamLead.GetData()); Console.Read(); } When you execute the above code snippet, the details of the two employees those are part of Steve’s team would be displayed in the console window. You can learn more on the Composite design pattern here. Related content feature What is Rust? Safe, fast, and easy software development Unlike most programming languages, Rust doesn't make you choose between speed, safety, and ease of use. Find out how Rust delivers better code with fewer compromises, and a few downsides to consider before learning Rust. By Serdar Yegulalp Nov 20, 2024 11 mins Rust Programming Languages Software Development how-to Kotlin for Java developers: Classes and coroutines Kotlin was designed to bring more flexibility and flow to programming in the JVM. Here's an in-depth look at how Kotlin makes working with classes and objects easier and introduces coroutines to modernize concurrency. By Matthew Tyson Nov 20, 2024 9 mins Java Kotlin Programming Languages analysis Azure AI Foundry tools for changes in AI applications Microsoft’s launch of Azure AI Foundry at Ignite 2024 signals a welcome shift from chatbots to agents and to using AI for business process automation. By Simon Bisson Nov 20, 2024 7 mins Microsoft Azure Generative AI Development Tools news Microsoft unveils imaging APIs for Windows Copilot Runtime Generative AI-backed APIs will allow developers to build image super resolution, image segmentation, object erase, and OCR capabilities into Windows applications. By Paul Krill Nov 19, 2024 2 mins Generative AI APIs Development Libraries and Frameworks Resources Videos