views:

206

answers:

1

I have problems to get generics to work in the following scenario:

Delphi provides the interface IComparable:

IComparable <T> = interface
  function CompareTo (Value : T) : Integer;
end;

I add another interface IPersistent:

IPersistent = interface
  function  ToString : String;
  procedure FromString (const Str : String);
end;

One example of a class implementing both interfaces:

TComparableString = class (TInterfacedObject, IComparable <String>, IPersistent)
strict private
  FValue : String;
public
  function  CompareTo (Value : String) : Integer;
  function  ToString : String;
  procedure FromString (const Str : String);
end;

Now for another generic class that has two interface constraints:

ISortIndex <VALUE_TYPE : IPersistent, IComparable> = interface
  ...
end;

And finally one implementation of that interface:

TSimpleSortIndex <VALUE_TYPE : IPersistent, IComparable> = class (TInterfacedObject, ISortIndex <VALUE_TYPE>)

  ...
end;

Now when I try to declare a sort index like that:

FSortIndex : ISortIndex <TComparableString>;

I get an error message

[DCC Error] Database.pas(172): E2514 Type parameter 'VALUE_TYPE' must support  interface 'IComparable'

I tried several things but can't get it to work.

Anyone in for some help? Thanks!

+4  A: 

Your TComparableString class doesn't implement the non-generic IComparable interface, so it doesn't satisfy the type constraint. You'll have to either change the constraint or implement IComparable.

Changing the constraint is probably the easiest way forward. I don't really know Delphi, but see if this works:

ISortIndex <VALUE_TYPE : IPersistent, IComparable<VALUE_TYPE>> = interface

TSimpleSortIndex <VALUE_TYPE : IPersistent, IComparable<VALUE_TYPE>> = 
    class (TInterfacedObject, ISortIndex <VALUE_TYPE>)

EDIT: I hadn't noticed that your TComparableString implemented IComparable<String> rather than IComparable<TComparableString>. Is that deliberate? Usually something is comparable to other instances of itself, not to a different type.

You could introduce another type parameter to ISortIndex/TSimpleSortIndex to indicate the type that VALUE_TYPE should be comparable to - but I suspect it's more sensible to change TComparableString.

Jon Skeet
I tried that. It results in the following error: "E2514 Type parameter 'VALUE_TYPE' must support interface 'IComparable<SortIndex.TComparableString>'"
Smasher
Ah, I see why. Editing...
Jon Skeet
I really meant to use TComparableString there instead of String. Everything seems to work fine now. Thanks for the quick and precise help!
Smasher