On 26.02.2013 09:36, Xiangrong Fang wrote:
Hi Sven,
Could you please give a simple example that shows what you said: require
that the type with which you specialize is a record. Then a class
operator in that record can be defined.
Let's suppose you have the following generic declaration:
=== example begin ===
type
generic TTreap<T1, T2> = class
// let's assume T1 requires "<"
end;
=== example end ===
If you use a record to specialize TTreap's T1 parameter then you can do
it the following way:
=== example begin ===
type
TMyRecord = record
// note: in mode objfpc the modeswitch advancedrecords is needed
class operator < (aLeft, aRight: TMyRecord): Boolean;
end;
// implementation:
class operator TMyRecord.<(aLeft, aRight: TMyRecord): Boolean;
begin
// compare aLeft and aRight
end;
// somewhere else
TTreapTMyRecordLongInt = specialize TTreap<TMyRecord, LongInt>;
=== example end ===
Now the generic will specialize without problem. If you want to
specialize other types that don't support class operators then you need
to wrap them inside a record, e.g.:
=== example begin ===
type
TRecTStringList = record
MyStringList: TStringList;
class operator < (aLeft, aRight: TRecTStringList): Boolean;
end;
=== example end ===
You can also use visibility modifiers like private or strict private to
hide the MyStringList field and make it accessible only through
properties. To simplyfy usage you can also define assignment operators.
E.g.:
=== example begin ===
type
// maybe it will also work with a TStringList if you use TStrings
instead...
TRecTStringList = record
private
fStringList: TStringList;
public
class operator := (aRight: TStringList): TRecTStringList;
class operator := (aRight: TRecStringList): TStringList;
end;
class operator TRecTStringList.:=(aRight: TStringList): TRecTStringList;
begin
Result.fStringList := aRight;
end;
class operator TRecTStringList.:=(aRight: TRecStringList): TStringList;
begin
Result := aRight.fStringList;
end;
// somewhere else:
var
sl: TStringList;
rec: TRecStringList;
begin
// setup sl
rec := sl;
// use rec in the tree
sl := rec;
end;
=== example end ===
It's not the nicest solution, but currently the only thing you can do.
Regards,
Sven
--
_______________________________________________
Lazarus mailing list
[email protected]
http://lists.lazarus.freepascal.org/mailman/listinfo/lazarus