TURBO PASCAL |
Новости
|
Конструктор
Вызывайте наследуемый Метод до реализации дополнительных действий: Procedure MyObject.Init(.....); begin {Вызов наследуемого конструктора Init} {Реализация дополнительных действий} end; Такая последовательность необходима по той простой причине, что вызов наследуемого конструктора приводит к обнулению всех дополнительных полей объекта MyObject. Если, например, Вы используете следующий фрагмент программы: type MyObject = object (TWindow) Value: Word; Ok : Boolean; Constructor Init(var Bounds: TRect; ATitle: TTitleStr; AValue: Word; AOk: Boolean); end; Constructor MyObject.Init; begin Inherited Init(Bounds, ATitle, wnNoNumber); Value := 16; Ok := True; end; то дополнительные поля Value и Ok получат нужные значения 16 и True. Однако, если обращение TWindow.Init (Bounds, ATitle, wnNoNumber); поставить после оператора Ok := True, в них будут помещены значения 0 и False. Из этого правила существует одно исключение, связанное с загрузкой коллекции из потока конструктором Load. Дело в том, что в наследуемом методе TCollection.Load реализуется следующий цикл: Constructor TCollection.Load (var S: TStream); begin ..... for I := 0 to Count - 1 do AtPut(I, GetItem(S)); end; Если элементами коллекции являются произвольные наборы двоичных данных (не объекты), Вам потребуется перед чтением очередного элемента сначала получить из потока его длину. Следующий пример иллюстрирует сказанное. type PDataCollection = ATDataCollection; TDataCollection = object (TStringCollection) ItemSize: Word; Constructor Load(var S: TStream); Function GetItem(var S: TStream): Pointer; Virtual; ..... end; Constructor TDataCollection.Load(var S: TStream); begin S.Read(ItemSize, SizeOf(ItemSize)); Inherited Load(S); end; Function TDataCollection.GetItem(var S: TStream): Pointer; var Item: Pointer; begin GetMem(Item, ItemSize); S.Read(Item, ItemSize); GetItem := Item; end; В этом примере конструктор Load сначала загружает из потока поле ItemSize, содержащее длину читаемого элемента. Затем вызывается конструктор TCollection.Load, в котором осуществляется вызов GetItem. Новый GetItem использует поле ItemSize, чтобы определить размер читаемых данных, и резервирует нужный буфер в динамической памяти. Разумеется, запись полиморфных коллекций в поток должна происходить в том же порядке, т.е. сначала записывается длина очередного элемента, а уже потом - его данные.
|
(с)Все права защищены По всем интересующим вопросам прошу писать на электронный адрес |