2

When trying the following code it will not compile as I receive this error:

Type parameter 'T' is not compatible with type TBase

I want this type constraint to support the Save method being typed to return the same class as itself.

TTest is not directly a TBase but TBase is the ancestor.

type
  TBase = class
  end;

  TBusiness<T: TBase> = class(TBase)
  public
    function Save: T; virtual; abstract;
  end;

  TTest = class(TBusiness<TTest>)
  end;
3
  • 1
    Your declaration of TTest says nothing of being a descendant of TBase. Also the Save method doesn't return the same type as itself (i.e. TBusiness<T>). It seems you have a basic misunderstanding of generics in Delphi. Commented Nov 12 at 11:18
  • 2
    @UweRaabe: Well, a TTest is a TBusiness<TTest>, and a TBusiness<T> is always a TBase. Therefore, a TTest is a TBase, and so TBusiness<TTest> satisfies the constraint TBussiness<T: TBase>. The problem here is that the declaration of TTest recursively refers to itself. The second TTest on the penultimate line refers to the TTest being declared at that moment. The compiler doesn't accept this (and it is certainly not a typical use of generics and classes). However, I do understand what the OP wants to achieve; this approach, however, isn't valid. Commented Nov 12 at 11:33
  • @AndreasRejbrand OK, when I drop my compiler glasses, where I immediately see that TTest is not fully defined at its usage, one could imagine what this all was meant to be. Commented Nov 12 at 16:55

1 Answer 1

0

A way to accomplish what I believe you're after is to use an interface, IBase, instead of the base class TBase. Like this:

type
  IBase = interface
  end;

  TBusiness<T> = class(TInterfacedObject, IBase)
  public
    function Save: T; virtual; abstract;
  end;

  TTest = class(TBusiness<TTest>, IBase)
  end;

Then Save will directly return an object of the exact right type, without any need for casting it (which I believe is the main "good" that you're after).

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.