Да, интерфейс наследуется подклассом.
Допустимо приведение из подкласса к интерфейсу.
Тем не менее, и извинения, если я неправильно читаю ваш вопрос, но если "а затем вернуться к исходному классу", значит. , .
У вас есть интерфейс I, класс A и класс B.
A реализует I, а B наследует A, возможно, вы можете, но ДЕЙСТВИТЕЛЬНО НЕ СЛЕДУЕТ приводить от A к B.
EDIT:
Вы хотите перейти от B к I и обратно к B. , , но у вас уже есть ссылка на B, если B - это то, что вы передаете своей функции, так что вам не нужно приводить от I к B (если речь не идет о другом объекте, тогда Нет, не делайте этого)
Переход от I к B аналогичен переходу от A к B, вы пытаетесь создать цепочку наследования, что на самом деле не следует делать. Необходимость сделать это - запах кода, он говорит вам, что вы должны попытаться решить эту проблему другим способом (возможно, изменив классы (например, добавив больше свойств / методов в I), или просто решив, что функция будет работать только с подклассом - работа с подклассом 'B' даст вам доступ ко всем методам A & I).
Можете ли вы отредактировать свой вопрос и добавить пример кода того, что вы пытаетесь сделать?
РЕДАКТИРОВАТЬ 2
procedure SendInterfaceObject(iobj:IMyInterFace);
begin
if (iobj is TSubMyObject) then
begin
//code here
end;
end;
Утверждение 'If' содержит плохую идею и нарушает принципы ОО. Если вам нужно сделать это, то либо
- Определение интерфейса
недостаточно, вы можете добавить
Тип свойства для интерфейса
позволяет вам (если iObj.SomeProperty
= 1) тогда. , .)
- Интерфейс просто не
исправить решение этой проблемы и
Вы должны передать ссылку как
TSubMyObject.
РЕДАКТИРОВАТЬ 3:
@ mghie: Я согласен с вами, но я не очень хорошо объяснил, что SomeProperty имеет некоторые данные, которые позволяют функции переходить туда, устраняя зависимость проверки типа. SomeProperty не должен «просто» заменять проверку типа (например, помещая имя класса в свойство, а затем проверяя имя класса). Это действительно точно такая же проблема.
Существует некоторое существенное отличие между подклассами, которые наследуют интерфейс. Эта разница должна быть выражена либо
- Предоставление некоторого элемента данных, который может
затем использовать в Brach
например.
if(item.Color = Red) then
item.ContrastColor := Blue;
else
item.ContrastColor := Red;
- Или через полиморфизм, например.
IEmployee определяет метод CalculatePay, TManager и TWorker реализуют IEmployee, каждый со своей логикой в методах CalculatePay.
Если целью было сделать что-то похожее на первый случай, полиморфизм может быть излишним (полиморфизм не решает все проблемы).
РЕДАКТИРОВАТЬ 4
Вы говорите "разделы // кода здесь имеют мало общего с объектом, который ему передается ..." Извините, но это утверждение неверно, если вам нужно заплатить Сотрудник, вам необходимо знать его 1) Код сотрудника 2) Данные о зарплате 3) Их банковские реквизиты и т. Д., Если вы выставляете счет на оплату необходимого вам счета 1) Счет-фактура 2) Сумма счета-фактуры 3) Код клиента, который нужно списать с счета и т. , , это идеальное место для полиморфизма .
Допустим, функция выполняет проверку интерфейса, чтобы определить, нужно ли «Учетным записям» что-то делать с объектом (например, оплатить сотруднику, выставить счет и т. Д.). Таким образом, мы могли бы вызвать функцию AccountsCheck. При проверке внутренних счетов у вас будет частичка логики, характерная для каждого подкласса (для оплаты сотрудника, для выставления счета ...). Это идеальный кандидат на полиморфизм.
На вашем интерфейсе (или на другом интерфейсе, или как виртуальный метод в подклассе) Определите метод "AccountsCheck". Затем каждый производный класс получает собственную реализацию проверки учетных записей.
Код перемещается из вашей огромной единственной функции AccountsCheck и в меньшие функции в каждом подклассе. Это делает код
- Более очевидно в намерении (каждый класс
содержит некоторую логику для
AccountsCheck)
- Вы реже сломаете подкласс
Логика Б при исправлении чего-либо в
Проверка учетных записей для C
- проще точно разобраться
какая логика для AccountsCheck подкласса B
есть, вы только чтобы проверить 20 строк
код в маленькой учетной записи, не 200
в общих учетных записях проверки)
Для этого есть и другие "веские причины", если кто-то хочет редактировать / оставлять комментарии, пожалуйста, сделайте это.
Если вам нужно разделить логику между реализациями AccountsCheck, создайте несколько служебных функций, не переопределяйте одно и то же колесо в каждой.
Полиморфизм - решение вашей проблемы.