русс | укр

Языки программирования

ПаскальСиАссемблерJavaMatlabPhpHtmlJavaScriptCSSC#DelphiТурбо Пролог

Компьютерные сетиСистемное программное обеспечениеИнформационные технологииПрограммирование

Все о программировании


Linux Unix Алгоритмические языки Аналоговые и гибридные вычислительные устройства Архитектура микроконтроллеров Введение в разработку распределенных информационных систем Введение в численные методы Дискретная математика Информационное обслуживание пользователей Информация и моделирование в управлении производством Компьютерная графика Математическое и компьютерное моделирование Моделирование Нейрокомпьютеры Проектирование программ диагностики компьютерных систем и сетей Проектирование системных программ Системы счисления Теория статистики Теория оптимизации Уроки AutoCAD 3D Уроки базы данных Access Уроки Orcad Цифровые автоматы Шпаргалки по компьютеру Шпаргалки по программированию Экспертные системы Элементы теории информации

Наследование


Дата добавления: 2015-07-09; просмотров: 532; Нарушение авторских прав


НАСЛЕДОВАНИЕ И ПОЛИМОРФИЗМ.

Класс ( подкласс) может наследовать переменные и методы другого класса (суперкласса), используя ключевое слово extends. Подкласс имеет доступ ко всем открытым переменным и методам (кроме private) родительского класса, как будто они находятся в подклассе. В то же время подкласс может иметь методы с тем же именем, параметрами и возвращаемым значением, что и методы суперкласса. В этом случае подкласс переопределяет методы родительского класса. Это часть механизма ООП, который называется полиморфизмом. В следующем примере переопределяемый метод show() находится в двух классах Bird и Eagle. По принципу полиморфизма вызывается метод, наиболее близкий к текущему объекту.

 

/* пример # 1 : наследование класса и переопределение

метода : BirdSample.java */

class Bird {

private String name;

private float price;

public Bird(float p, String str) { //конструктор

name = str;

price = p;

}

public float getPrice(){

return price;

}

public g getName(){ Strin

return name;

}

void show(){

System.out.println("название: " + name

+ ", цена: " + price);

}

}

class extends Bird { Eagle

private boolean fly;

public Eagle(float p, String str, boolean f) {

super(p, str); //вызов конструктора суперкласса

fly = f;

}

void show(){

System.out.println("название:" + getName()

+ ", цена: " + getPrice() + ", полет:" + fly);

}

}

public class BirdSample {

public static void main(String[] args) {

Bird b1 = new Bird(0.85F, "Гусь");

Bird b2 = new Eagle(10.55F, "Белый Орел", true);

b1.show(); // вызов show() класса Bird

b2.show(); // вызов show() класса Eagle

}

}

 

Объект b1 создается при помощи вызова конструктора класса Bird, и, соответственно, при вызове метода show() вызывается версия метода из класса Bird. При создании объекта b2 ссылка типа Bird инициализируется объектом типа Eagle. При таком способе инициализации ссылка на суперкласс получает доступ к методам, переопределенным в подклассе. При объявлении совпадающих по сигнатуре полей в суперклассе и подклассах их значения не переопределяются и никак не пересекаются, то есть существуют в одном объекте независимо друг от друга. В этом случае задача извлечения требуемого значения определенного поля, принадлежащего классу в цепочке наследования, ложится на программиста.



 

/* пример # 2 : доступ к полям с одинаковыми именами

при наследовании : DemoAB.java */

class A {

int x = 1, y = 2;

public A() {

y = getX();

System.out.println("в классе A после вызова"

+ " getX() x=" + x + " y=" + y);

}

public int getX(){

System.out.println("в классе A");

return x;

}

}

class B extends A {

int x = 3, y = 4;

public B() {

System.out.println("в классе B x=" + x

+ " y=" + y);

}

public int getX(){

System.out.println("в классе B");

return x;

}

}

public class DemoAB {

public static void main (String[] args) {

A objA = new B();

B objB = new B();

System.out.println(objA.x);

System.out.println(objB.x);

}

}

 

В результате выполнения данного кода последовательно будет выведено:

 

в классе B

в классе A после вызова getX() x=1 y=0

в классе B x=3 y=4

в классе B

в классе A после вызова getX() x=1 y=0

в классе B x=3 y=4

x=1

x=3

 

В случае создания объекта objA инициализацией ссылки на класс А объектом класса В был получен доступ к полю х класса А. Во втором случае при создании объекта objB класса В был получен доступ к полю х класса В. Однако, воспользовавшись преобразованием типов вида: ((B)objA).x или ((A)objB).x, легко можно получить доступ к полю х из соответствующего класса. Одну из сторон полиморфизма методов иллюстрирует конструктор класса А в виде:

 

public A() {

y = getX();

}

 

Метод getX() содержится как в классе A, так и в классе В. При создании объекта класса В одним из способов:

A objA = new B();

B objB = new B();

в любом случае сначала вызывается конструктор класса А. Но так как создается объект класса В, то вызывается метод getX(), соответственно принадлежащий классу В, который в свою очередь оперирует полем х, еще не проинициализированным для класса В. В результате у получит значение х по умолчанию, т.е. нуль. Нельзя создать подкласс для класса, объявленного со спецификатором final:

 

// класс First не может быть суперклассом

final class First {/*код*/}

// сл класс н едующий евозможен

class Second extends First{/*код*/}

 

Использование super и this Ключевое слово super используется для вызова конструктора суперкласса и для доступа к члену суперкласса. Например:

 

super(список_параметров); /* вызов конструктора суперкласса с передачей параметров или без нее*/

super.i = n; /* обращение к атрибуту суперкласса */

super.methodName(); // вызов метода суперкласса

 

Вторая форма super подобна ссылке this на экземпляр класса. Третья форма специфична для Java и обеспечивает вызов переопределенного метода, причем если в суперклассе этот метод не определен, то будет осуществляться поиск по цепочке наследования до тех пор, пока метод не будет найден. Каждый экземпляр класса имеет неявную ссылку this на себя, которая передается также и методам. После этого можно, например, вместо артибута price писать this.price, хотя и не обязательно. Следующий код показывает, как, используя this, можно строить одни конструкторы на основе других.

 

// пример # 3 : this в конструкторе : Locate3D.java

class a D { Loc te3

private int x, y, z;

public Locate3D(int x, int y, int z) {

this.x = x;

this.y = y;

this.z = z;

}

public cate3D() { Lo

this(-1, -1, -1);

}

}

 

В этом классе второй конструктор для завершения инициализации объекта обращается к первому конструктору. Такая конструкция применяется в случае, когда в классе имеется несколько конструкторов и требуется добавить конструктор по умолчанию. Ссылка this используется в методе для уточнения того, о каких именно переменных x и y идет речь в каждом отдельном случае, а конкретно для доступа к переменной класса из метода, если в методе есть локальная переменная с тем же именем. Инструкция this() должна быть единственной в вызывающем конструкторе и быть первой по счету выполняемой операцией.



<== предыдущая лекция | следующая лекция ==>
Список использованных источников | Переопределение методов и полиморфизм


Карта сайта Карта сайта укр


Уроки php mysql Программирование

Онлайн система счисления Калькулятор онлайн обычный Инженерный калькулятор онлайн Замена русских букв на английские для вебмастеров Замена русских букв на английские

Аппаратное и программное обеспечение Графика и компьютерная сфера Интегрированная геоинформационная система Интернет Компьютер Комплектующие компьютера Лекции Методы и средства измерений неэлектрических величин Обслуживание компьютерных и периферийных устройств Операционные системы Параллельное программирование Проектирование электронных средств Периферийные устройства Полезные ресурсы для программистов Программы для программистов Статьи для программистов Cтруктура и организация данных


 


Не нашли то, что искали? Google вам в помощь!

 
 

© life-prog.ru При использовании материалов прямая ссылка на сайт обязательна.

Генерация страницы за: 0.208 сек.