<html>
  <head>
    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
  </head>
  <body smarttemplateinserted="true">
    <div id="smartTemplate4-template">Hi,</div>
    <div>
      <blockquote type="cite">
        <pre class="moz-quote-pre" wrap="">The problem is that, we like OOP inheritance  but when we extend classes we are forced into a single hierarchy. </pre>
      </blockquote>
    </div>
    <div><br>
      there is another way to extend classes without inheritance: type
      helpers<br>
      <p>Traits are like reverse type helpers. With the type helper you
        first declare the class and then the extending helper.<br>
        <br>
        === code begin === <br>
        type<br>
          TTest = class(TObject)<br>
          public<br>
            procedure test(a: integer);<br>
          end;<br>
          TTrait = class helper for TTest<br>
            procedure test2;<br>
          end;<br>
        <br>
        procedure TTest.test(a: integer);<br>
        begin<br>
          writeln(a);<br>
        end;<br>
        <br>
        procedure TTrait.test2;<br>
        begin<br>
          test(10);<br>
        end;<br>
        //var x: ttest2;<br>
        //x.test2    <br>
        <br>
        === code end === <br>
      </p>
      <div><br>
      </div>
      <div>With traits you could first define the extension, and then
        the class:<br>
      </div>
      <div><br>
      </div>
      <div>=== code begin === <br>
        type<br>
          TTrait = trait<br>
            procedure test2;<br>
          end;<br>
          TTest = class(TObject, TTrait)<br>
          public<br>
            procedure test(a: integer);<br>
          end;<br>
        <br>
        procedure TTest.test(a: integer);<br>
        begin<br>
          writeln(a);<br>
        end;<br>
        <br>
        procedure TTrait.test2;<br>
        begin<br>
          test(10); //here it needs to know the test function exist.
        Perhaps declare it in the the trait, too? <br>
        end;<br>
        //var x: ttest2;<br>
        //x.test2    <br>
        === code end === </div>
      <br>
    </div>
    <div>But otherwise, it looks exactly the same</div>
    <div><br>
    </div>
    <div>Perhaps the type helper code could be reused for traits</div>
    <div><br>
    </div>
    <div><br>
    </div>
    <div><br>
    </div>
    <div><br>
    </div>
    <div><br>
    </div>
    <div>Cheers,<br>
      Benito <br>
    </div>
    <div><br>
    </div>
    <div><br>
    </div>
    <div class="moz-cite-prefix">On 18.02.21 04:37, Ryan Joseph via
      fpc-pascal wrote:<br>
    </div>
    <blockquote type="cite"
      cite="mid:B0407BE2-AD90-4FCE-9A22-04F34749D1C2@gmail.com">
      <pre class="moz-quote-pre" wrap="">


</pre>
      <blockquote type="cite">
        <pre class="moz-quote-pre" wrap="">On Feb 17, 2021, at 9:59 AM, Adriaan van Os via fpc-pascal <a class="moz-txt-link-rfc2396E" href="mailto:fpc-pascal@lists.freepascal.org"><fpc-pascal@lists.freepascal.org></a> wrote:

1. multiple inheritance is nice to have, but it has the big issue that the inheritance tree becomes an inheritance graph and that makes overrules ambiguent.
2. interfaces don't have this issue with multiple inheritance, because they just declare, not implement
3. but that is also the weakness of interfaces,  as we don't want to reimplement the same code each time
4. so, we really want an multiple-inheritance graph at the declaration level with clear tree-like unambigous inheritance paths at the implementation level
5. thus, the idea is to "push-in" implementation code into an interface that integrates fully at the declaration level but is independent at the implementation level.
</pre>
      </blockquote>
      <pre class="moz-quote-pre" wrap="">
I would say that's right.

The problem is that, we like OOP inheritance  but when we extend classes we are forced into a single hierarchy. We could use existing delegation patterns and dot-notation  like obj.helper.DoSomething or by breaking out entirely and using plain functions  but then we lose some of what makes OOP nice, which is, simply saying "something.DoFunction". It may be trivial in terms of typing but it's elegant and in my opinion clean code which is not tedious to write makes happy and more productive.


Here's a more practical example but there are other possibilities for composition patterns (I'l think of examples later). I copied this from the RTL and made some changes. Assume you have this hierarchy and you want to add some methods/data to JPEG and GIF images but not TIFF and PNG (they have some special compression needs or something like that). What we would do now is probably just dump them into TCustomBitmap (and bloat TIFF/PNG)  or make another subclass just to store the extra methods (which is useless besides being a method store for 2 specific other classes). 

What I want with traits is that I can extend those 2 classes with specific functionality, still retain the object-orientedness of the syntax and not get trapped trying to inject stuff into a hierarchy where it doesn't really belong anyways.


TTIFFBitmap   TPNGBitmap   TJPEGBitmap   TGIFBitmap
                | 
                TCustomBitmap
                | 
                TRasterImage
                | 
                TGraphic
                | 
                TPersistent
                | 
                TObject


Regards,
        Ryan Joseph

_______________________________________________
fpc-pascal maillist  -  <a class="moz-txt-link-abbreviated" href="mailto:fpc-pascal@lists.freepascal.org">fpc-pascal@lists.freepascal.org</a>
<a class="moz-txt-link-freetext" href="https://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal">https://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal</a>
</pre>
    </blockquote>
  </body>
</html>