Обновление: выпотрошил вопрос более простым примером, на который нет ответа в первоначально принятом ответе.
Учитывая следующий класс и его предок:
TComputer = class(TObject)
public
constructor Create(Teapot: string='');
end;
TCellPhone = class(TComputer)
public
constructor Create(Cup: Integer); overload; virtual;
constructor Create(Cup: Integer; Teapot: string); overload; virtual;
end;
Прямо сейчас TCellPhone
имеет 3 видимых конструктора:
- Чашка: целое число
- Чашка: целое число; Чайник: шнурок
- Чайник: строка = ''
Что мне делать с TCellPhone
, чтобы конструктор предка (Teapot: string = ''
) не был виден, оставив только объявленные конструкторы:
- Чашка: целое число
- Чашка: целое число; Чайник: шнурок
Примечание. Обычно простой акт наличия конструктора-потомка скрывает предка:
TCellPhone = class(TComputer) public constructor Create(Cup: Integer); virtual; end;
- Чашка: целое число
И если вы хотите сохранить и конструктор-предок, и потомок, вы должны отметить потомка как
overload
:TCellPhone = class(TComputer) public constructor Create(Cup: Integer); overload; virtual; end;
- Чашка: целое число
- Чайник: строка = ''
В примере кода этого вопроса Delphi ошибочно принимает мои overload
ключевые слова:
TCellPhone = class(TComputer)
public
constructor Create(Cup: Integer); overload; virtual;
constructor Create(Cup: Integer; Teapot: string); overload; virtual;
end;
думать, что:
- я хочу перегрузить свои конструкторы с помощью предка,
- когда я действительно хочу перегрузить его родным братом
Как скрыть конструктор предка?
Примечание. Может оказаться невозможным скрыть невиртуальный конструктор-предок, используя язык Delphi, как он определен в настоящее время. "Невозможно" - правильный ответ.
Попытка ответа (не удалось)
Я попытался пометить конструкторы-потомки с помощью reintroduce
(возвращаясь к моему режиму случайного добавления ключевых слов, пока он не сработает):
TCellPhone = class(TComputer)
public
constructor Create(Cup: Integer); reintroduce; overload; virtual;
constructor Create(Cup: Integer; Teapot: string); reintroduce; overload; virtual;
end;
Но это не сработало, все три конструктора все еще видны. :(
Исходный вопрос
у меня есть объект, который происходит от класса, конструкторы которого не хотят видеть:
TEniac = class(TObject)
constructor Create(PowerCord: TPowerCord=nil); //calls inherited Create
TComputer = class(TEniac) ...
constructor Create(PowerCord: TPowerCord=nil); //calls inherited Create(nil)
TCellPhone = class(TComputer)
constructor Create(sim: TSimChip; UnlockCode: Integer); //calls inherited Create(nil)
TiPhone = class(TCellPhone)
constructor Create(sim: TSimChip); //calls inherited Create(sim, 0)
Примечание. Это гипотетический пример. Как и в реальном мире, объекты-предки нельзя изменить без нарушения существующего кода.
Теперь, когда кто-то использует TiPhone
, я не хочу, чтобы он даже мог видеть конструктор из TEniac
:
iphone := TiPhone.Create(powerCord);
Что еще хуже: если они вызовут этот конструктор, они полностью упустят мой конструктор и все, что сделано между ними. Довольно легко вызвать неправильный конструктор, все они видны в автозавершении кода IDE и будут скомпилированы:
TiPhone.Create;
и они получают совершенно недопустимый объект.
я мог бы изменить TCellPhone
, чтобы исключить эти конструкторы:
TCellPhone.Create(PowerCord: TPowercord)
begin
raise Exception.Create('Don''t use.');
end;
Но разработчики не поймут, что вызывают не тот конструктор, пока заказчик однажды не обнаружит ошибку и не оштрафует нас на миллиарды долларов. Фактически, я пытаюсь найти везде, где вызываю неправильный конструктор, но я не могу понять, как заставить Delphi сказать мне!