
- •Ссылки на объекты наследуемого и наследующего классов
- •Пример:
- •Пример:
- •class Demo
- •Виртуальные методы, переопределение методов
- •Виртуальные методы, переопределение методов
- •Ссылочная переменная может ссылаться на различные типы объектовмогут быть вызваны разные версии метода.
- •При определении виртуального метода
- •Пример: использование виртуального метода и его переопределенных версий.
- •//наследующий класс
- •class Demo
- •В каждом случае вызываемая версия метода определяется динамически
- •Идентификация типа во время выполнения программы
- •Оператор проверки типа is
- •public class IsTest
- •Когда нужно и можно переопределять
- •Правила переопределения методов
- •Нельзя путать переопределение и перегрузку методов.

Ссылки на объекты наследуемого и наследующего классов
В C# соблюдается строгий контроль типов.
Автоматическое приведение типов не допустимо для переменных ссылочного типа.
ссылочная переменная не может ссылаться на экземпляр другого класса, даже если эти классы идентичны
по своей структуре.
1

Пример:
class X
{
int a;
public X (int i) {a=i;}
}
class Y
{
int a;
public Y (int i) {a=i;}
}
class Demo
{
public static void Main ()
{
X x1 = new X (123);
X x2;
Y y = new Y (456);
x2 = x1; // Допустимая операция, переменные одного типа
x2 = y; //ОШИБКА! Разные типы переменных
}
}
2

Несмотря на строгий контроль типов, C# допускает следующее исключение:
Ссылочной переменной наследуемого класса можно присвоить ссылку на экземпляр любого наследующего класса
parentObj=childObj;
НО (!) возможность доступа к члена класса зависит
от типа самой ссылочной переменной,
а не от типа объекта, на который она
ссылается.
Поэтому
если переменной типа наследуемого класса присвоить ссылку на объект наследующего класса,
то с помощью этой переменной можно будет
обратиться только к тем членам класса,
которые определены в наследуемом классе.
3

Пример:
class X
{
public int a;
public X (int i) {a=i;}
}
class Y : X
{
public int b;
public Y (int i, int j) : base (j)
{
b=i;
}
}
4

class Demo
{
public static void Main ()
{
Xx1 = new X (123);
Xx2;
Y y = new Y (4,5);
x2 = x1;
//Допустимая операция, переменные одного типа x2 = y;
//Допустимо – класс Y наследует класс X
x2.a =1;
// Допустимая операция, переменные одного типа
x2.b =2;
//ОШИБКА! В классе Х не определена переменная b
}
}
5

Виртуальные методы, переопределение методов
Рассматривается иерархия классов.
Метод ,
при определении которого в наследуемом классе было указано ключевое слово virtual, и
который был переопределен в одном и более
наследующих классах,
называется виртуальным.
Каждый наследующий класс может содержать собственную (переопределенную!) версию виртуального метода.
6

Виртуальные методы, переопределение методов
Отличие от «обычных» методов:
выбор версии метода выполняется в соответствии с типом объекта, на который ссылается переменная.
Выбор выполняется при вызове метода во время выполнения программы, а не во время трансляции.
Это динамический выбор вызываемого метода – динамическое связывание.
7

Ссылочная переменная может ссылаться на различные типы объектовмогут быть вызваны разные версии метода.
!!! Не тип ссылочной переменной,
а тип объекта (на который она ссылается),
определяет то, какая версия виртуального метода будет вызвана:
Если класс
содержит виртуальный метод,
от этого класса были наследованы другие
классы, в которых определены свои версии метода,
тогда при ссылке переменной типа наследуемого класса на различные типы объектов
вызываются различные версии виртуального
метода.
8

При определении виртуального метода
в наследуемом классе указывается модификатор virtual,
При переопределении виртуального метода
в наследующем классе указывается модификатор override.
Виртуальный метод не может быть определен
смодификаторами static или abstract.
Процесс определения виртуального метода внутри наследующего класса, при котором
частично или полностью изменяется тело метода,
а имя, список параметров остаются прежними,
называется переопределением метода.
9

Пример: использование виртуального метода и его переопределенных версий.
using System;
namespace virt1
{
class A
{
// виртуальный метод в наследуемом классе
public virtual void show ( )
{
Console.WriteLine("метод, определенный в классе A");
}
}
10