Об этом уже спрашивали несколькими разными способами, но я еще не нашел своего ответа.
Кто-нибудь может мне кое-что прояснить. Использование: Delphi XE2
У меня довольно большой BaseObject, который я использую почти для всего. Наряду с этим у меня есть общий список - BaseList.
Изменения выглядят следующим образом:
TBaseObject = class
... a lot of properties and methods ...
end;
TBaseList<T: TBaseObject> = class(TObjectList<T>)
... some properties and methods ...
end;
Я недавно попытался изменить объявление TBaseList с очень старого TStringList, используя свойство Objects [] ... на этот никогда не более универсальный список универсальных шаблонов TObjectList.
Но я столкнулся с некоторыми проблемами. BaseUnit - это один файл ... и каждый раз, когда я спускаюсь по моему BaseObject, я также составляю специальный список, чтобы следовать ему.
Итак, я бы сделал что-то вроде:
TCustomer = class(TBaseObject)
... customer related stuff ...
end;
TCustomerList<T: TCustomer> = class(TBaseList<T>)
... customer list specific stuff ...
end;
Но теперь я хотел бы, чтобы объект содержал список - который может содержать любой объект. И я подумал, что смогу сделать это вот так
TControlObject = class(TBaseobject)
FGenList: TBaseList<TBaseObject>;
end;
. Поскольку BaseList и BaseObject находятся на вершине моей иерархии, я предположил, что такой List сможет содержать любой список, который я мог придумать.
Но у меня такое ощущение, что именно здесь я проигрываю ...
a TBaseList
почему-то несопоставим с TCustomerList
...
Даже если TCustomerList
и TCustomer
являются потомками моей базы.
Я надеялся, что смогу использовать дженерики в базовом списке для создания новых объектов.
т.е. используя T.Create
в методе заполнения.
Вот пример полной иерархии:
Base Unit;
TBaseObject = class
end;
TBaseList<T:TBaseObject> = class(TObjectList<T>)
end;
CustomCustomer Unit;
TCustomCustomer = class(TBaseObject)
end;
TCustomCustomerList<T:TCustomCustomer> = class(TBaseList<T>)
end;
Customer Unit;
TCustomer = class(TCustomCustomer)
end;
TCustomerList<T:TCustomer> = class(TCustomCustomerList<T>)
end;
CustomPerson Unit;
TCustomPerson = class(TBaseObject)
end;
TCustomPersonList<T:TCustomPerson> = class(TBaseList<T>)
end;
Person Unit;
TPerson = class(TCustomPerson)
end;
TPersonList<T:TPerson> = class(TCustomPersonList<T>)
end;
Учитывая приведенную выше иерархию - почему я не могу:
var
aList : TBaseList<TBaseObject>; // used as a list parameter for methods
aPersonList : TPersonList<TPerson>;
aCustomerList : TCustomerList<TCustomer>;
begin
aPersonList := TPersonList<TPerson>.Create;
aCustomerList := TCustomerList<TCustomer>.Create;
aList := aCustomerList; <-- this FAILS !! types not equal ..
end;
Вызов процедуры, которая обрабатывает базовый класс для всех списков, терпит неудачу одинаково ...
Procedure LogStuff(SomeList : TBaseList<TBaseObject>)
begin
writeln(Format( 'No. Elements in list : %d',[SomeList.Count]));
end;
Может ли кто-нибудь удари меня и скажи, что я здесь делаю не так?