How do I create a generic list of objects from a specific base class?

   TMyDataList<T: TBaseDatafile, constructor> = class(TObjectList<TBaseDatafile>)
   public
      constructor Create;
      procedure upload(db: TDataSet);
   end;

      

I read in a blog post (I don't remember where now) that this is a way to declare a generic class with a specific base type for a generic object. And the compiler will accept it just fine. But when I try to use it, it decides not to cooperate.

type
   TDescendantList = TMyDataList<TDescendantDatafile>;

      

This is giving me a compiler error.

[DCC Error] my_database.pas (1145): E2010 Incompatible types: "TDescendantDatafile" and "TBaseDatafile"

The thing is, 1145 isn't even a valid string. This file ends with # 1142, and the type declaration it complains is at line # 20. This makes me wonder if the compiler has been compromised. Or am I just not quite correct syntax? Does anyone know a way to make this work?

EDIT: Jim noted that it compiles fine when he tried it. A little more information: I have a base data file type and a generic list declared in the same block, while TDescendantDatafile is in the second block and TDescendantList is defined in the third. I have already found and reported a bug in the D2009 compiler, which uses generics to stuff types on multiple devices. It could be related. Can anyone confirm this?

+1


source to share


2 answers


The definition of TObjectList <> is:

TObjectList<T: class> = class(TList<T>)

      

So, you like to do something like:

TMyDataList<T: TBaseDatafile> = class(TObjectList<T>)

      

Unfortunately, this won't work. Fortunately:

TMyDataList<T: class> = class(TObjectList<T>)

      



Works, but this is probably not what you want. Because it won't use the class type. I really think the class specifier is a little weird here. (TObject should have avoided problems). But that won't help you.

Then the following works are performed again:

  TBaseDataFile = class
  end;

  TDescendantDatafile = class (TBaseDataFile)
  end;

  TMyDataList<T: TBaseDataFile> = class(TObjectList<TBaseDataFile>)
  public
    constructor Create;
  end;

      

Are you sure TDescendantDataFile inherits from TBaseDataFile?

In the old days (read turbo pascal) sometimes line numbers where wrong because of invisible characters. But I don't think this is still relevant.

+2


source


When TDescendantDatafile descends from TBaseDataFile it works fine on my machine. Check the class hierarchy.



If I change the ancestor of TDescendantDatafile, then I get the same error and it gives me the correct line numbers. If the compiler gives you incorrect line numbers, close the project, open it, and do a full build.

+1


source







All Articles