Composition over inheritance: Difference between revisions

Content deleted Content added
m Removing link(s) undefined (XFDcloser)
 
(5 intermediate revisions by 5 users not shown)
Line 76:
 
===Composition and interfaces===
The C++ examples in this section demonstrate the principle of using composition and interfaces to achieve code reuse and polymorphism. Due to the C++ language not having a dedicated keyword to declare interfaces, the following C++ example uses inheritance from a pure [[abstract base class]]. For most purposes, this is functionally equivalent to the interfaces provided in other languages, such as Java<ref name=Bloch>{{cite book | title= "Effective Java: Programming Language Guide" |last=Bloch| first=Joshua| publisher=Addison-Wesley | edition=third | isbn=978-0134685991| year=2018}}</ref>{{rp|87}} and C#.<ref name=Price>{{cite book |last=Price | first=Mark J. |title=C# 8.0 and .NET Core 3.0 – Modern Cross-Platform Development: Build Applications with C#, .NET Core, Entity Framework Core, ASP.NET Core, and ML.NET Using Visual Studio Code | date=2022 | publisher= Packt |isbn= 978-1-098-12195-2}}</ref>{{rp|144}}
 
Introduce an abstract class named {{code|VisibilityDelegate}}, with the subclasses {{code|NotVisible}} and {{code|Visible}}, which provides a means of drawing an object:
Line 211:
 
==Benefits==
To favor composition over inheritance is a design principle that gives the design higher flexibility. It is more natural to build business-___domain classes out of various components than trying to find commonality between them and creating a family tree. For example, an accelerator pedal and a steering wheel share very few common [[Trait (computer programming)|traits]], yet both are vital components in a car. What they can do and how they can be used to benefit the car isare easily defined. Composition also provides a more stable business ___domain in the long term as it is less prone to the quirks of the family members. In other words, it is better to compose what an object can do (''[[has-a]]'') than extend what it is (''[[is-a]]'').<ref name="FHDPs">{{cite book
| last1 = Freeman
| first1 = Eric
Line 283:
Some languages provide specific means to mitigate this:
 
* [[C Sharp (programming language)|C#]] provides default interface methods since version 8.0 which allows to define body to interface member.<ref>{{cite web | url=https://docs.microsoft.com/en-us/dotnet/csharp/whats-new/csharp-8#default-interface-methods | title=What's new in C# 8.0 | website=Microsoft Docs | publisher=Microsoft | access-date=2019-02-20}}</ref><ref name=Price>{{cite book |last=Price | first=Mark J. |title=C# 8.0 and .NET Core 3.0 – Modern Cross-Platform Development: Build Applications with C#, .NET Core, Entity Framework Core, ASP.NET Core, and ML.NET Using Visual Studio Code | publisher= Packt |isbn= 978-1-098-12195-2}}</ref>{{rp|28-2928–29}}<ref name=Skeet>{{cite book |last=Skeet|first=Jon|title= C# in Depth |date=23 March 2019 |publisher= Manning |isbn= 978-1617294532}}</ref>{{rp|38}}<ref name=Albahari>{{cite book |last=Albahari |first=Joseph |title= C# 10 in a Nutshell |date=2022 |publisher= O'Reilly |isbn= 978-1-098-12195-2}}</ref>{{rp|466-468466–468}}
* [[D (programming language)|D]] provides an explicit "alias this" declaration within a type can forward into it every method and member of another contained type.<ref>{{cite web | url=https://dlang.org/spec/class.html#alias-this | title=Alias This | website=D Language Reference| access-date=2019-06-15}}</ref>
* [[Dart (programming language)|Dart]] provides mixins with default implementations that can be shared.
* [[Go (programming language)|Go]] type embedding avoids the need for forwarding methods.<ref>{{cite web | url=https://golang.org/doc/effective_go.html#embedding | title=''(Type)'' Embedding | website=The Go Programming Language Documentation | access-date=2019-05-10}}</ref>
* [[Java (programming language)|Java]] provides default interface methods since version 8.<ref name=Bloch>{{cite book | title= "Effective Java: Programming Language Guide" |last=Bloch| first=Joshua| publisher=Addison-Wesley | edition=third | isbn=978-0134685991| year=2018}}</ref>{{rp|104}} Project Lombok<ref>https://projectlombok.org {{Bare URL inline|date=August 2024}}</ref> supports delegation using the {{code|@Delegate}} annotation on the field, instead of copying and maintaining the names and types of all the methods from the delegated field.<ref>{{cite web | url=https://projectlombok.org/features/experimental/Delegate | title=@Delegate | website=Project Lombok | access-date=2018-07-11}}</ref>
* [[Julia (programming language)|Julia]] macros can be used to generate forwarding methods. Several implementations exist such as Lazy.jl<ref>{{cite web | url=https://github.com/MikeInnes/Lazy.jl | title=MikeInnes/Lazy.jl | website=[[GitHub]] }}</ref> and TypedDelegation.jl.<ref>{{cite web | url=https://github.com/JeffreySarnoff/TypedDelegation.jl | title=JeffreySarnoff/TypedDelegation.jl | website=[[GitHub]] }}</ref><ref>{{cite web |title=Method forwarding macro |url=https://discourse.julialang.org/t/method-forwarding-macro/23355 |website=JuliaLang |access-date=18 August 2022 |language=en |date=20 April 2019}}</ref>
* [[Kotlin (programming language)|Kotlin]] includes the delegation pattern in the language syntax.<ref>{{cite web | url=https://kotlinlang.org/docs/reference/delegated-properties.html | title=Delegated Properties | website=Kotlin Reference | publisher=JetBrains | access-date=2018-07-11}}</ref>
* [[PHP]] supports [[Traits (computer science)|traits]], since PHP 5.4.<ref>{{cite web |title=PHP: Traits |url=https://www.php.net/manual/en/language.oop5.traits.php |website=www.php.net |access-date=23 February 2023}}</ref>