[fpc-pascal] class inheritance and type incompatibility

Sven Barth pascaldragon at googlemail.com
Sun Sep 29 18:41:40 CEST 2013


On 29.09.2013 11:47, Xiangrong Fang wrote:
> 2013/9/29 Sven Barth <pascaldragon at googlemail.com
> <mailto:pascaldragon at googlemail.com>>
>
>
>     I would suggest you to add an additional protected virtual method to
>     TTree<> which is called from TTree<>.Clone and you override that in
>     your descendant classes.
>
>
> Could
> ​ you please give an example how to do this?  I tried the following:
>
> === code start ===
> function TTree.DoClone: TTree; //protected, virtual
> begin
>    Result := TSelfClass(Self.ClassType).Create(Data, FParent);
> end;
>
> function TTree.Clone: TTree;
> var
>    node: TTree;
> begin
>    Result := DoClone;
>    node := FirstChild;
>    while node <> nil do begin
>      node.Clone.Remove(Result);
>      node := node.NextSibling;
>    end;
> end;
> === code end ===
>
> However, this does not work, because it seems that I cannot make any
> generic method virtual!  In TIntTree, I have to write:
>
> function TIntTree.DoClone: TIntTree;
>
> As it is not possible to write TTree outside of the generic definition.

This should do it:

=== code begin ===

type
   generic TTree<T> = class
   protected type
     TSelfType = TTree;
   protected
     procedure DoClone(aNode: TSelfType); virtual;
   public
     function Clone: TSelfType;
   end;

procedure TTree.DoClone(aNode: TSelfType);
begin
   (* empty *)
end;

function TTree.Clone: TSelfType;
var
   n: TTree;
begin
   Result := TSelfType(Self.ClassType).Create(Data, FParent);

   node := FirstChild;
   while node <> nil do begin
     node.Clone.Remove(Result);
     node := node.NextSibling;
   end;

   DoClone(Result);
end;


type
   TIntTree = class(specialize TTree<Integer>)
   protected
     procedure DoClone(aNode: TSelfType; override;
   end;

procedure TIntTree.DoClone(aNode: TSelfType);
begin
   inherited;
   (* whatever *)
end;

=== code end ===

Regards,
Sven



More information about the fpc-pascal mailing list