Successfully reported this slideshow.
Your SlideShare is downloading. ×

Урок 17. Внутренние классы и дженерики в языке Java

Ad
Ad
Ad
Ad
Ad
Ad
Ad
Ad
Ad
Ad
Ad

Check these out next

1 of 60 Ad

Урок 17. Внутренние классы и дженерики в языке Java

Download to read offline

Урок 17. Внутренние классы и дженерики в языке Java.
Что такое внутренний класс. Типы внутренних классов.
Обычный внутренний класс. Локальный и анонимный класс
Статический вложенный класс. Дженерики.
Лекции, задания, видео, тесты и вопросы на:
https://www.examclouds.com/ru/java/java-core-russian/lesson14
Подписывайтесь на страницу:
https://www.facebook.com/Examclouds
Подписывайтесь на канал
https://www.youtube.com/c/tatyanamilkina

Урок 17. Внутренние классы и дженерики в языке Java.
Что такое внутренний класс. Типы внутренних классов.
Обычный внутренний класс. Локальный и анонимный класс
Статический вложенный класс. Дженерики.
Лекции, задания, видео, тесты и вопросы на:
https://www.examclouds.com/ru/java/java-core-russian/lesson14
Подписывайтесь на страницу:
https://www.facebook.com/Examclouds
Подписывайтесь на канал
https://www.youtube.com/c/tatyanamilkina

Advertisement
Advertisement

More Related Content

Slideshows for you (16)

Similar to Урок 17. Внутренние классы и дженерики в языке Java (20)

Advertisement

Recently uploaded (15)

Урок 17. Внутренние классы и дженерики в языке Java

  1. 1. 1. Что такое внутренний класс 2. Типы внутренних классов 3. Обычный внутренний класс 4. Локальный и анонимный класс 5. Статический вложенный класс 6. Дженерики www.examclouds.com
  2. 2. Что такое внутренний класс  Внутренний класс (inner class) - это класс определенный внутри другого класса.  Область действия внутреннего класса ограничена областью действия внешнего класса.  Если класс В определен в классе А, то класс B не может существовать независимо от класса А.  Внутренний класс имеет доступ к членам (в том числе закрытым) того класса, в который он объявлен. www.examclouds.com
  3. 3. Типы внутренних классов  Обычный внутренний класс (regular inner class or member class)  Локальный класс (method-local inner class)  Анонимный класс (anonymous inner class)  Статический вложенный класс (static nested class) www.examclouds.com
  4. 4. Обычный внутренний класс  Внутренний класс определяется в области действия внешнего класса.  Чтобы создать объект внутреннего класса, должен существовать объект внешнего класса.  Внутренний и внешний класс имеют доступ ко всем членам класса друг друга (даже private). www.examclouds.com
  5. 5. Пример обычного внутреннего класса public class Town { private String postCode = "33333"; public class Street { public void printAddress() { System.out.println("Town is " + Town.this); System.out.println("PostCode is " + postCode); System.out.println("Street is " + this); } } public void createStreet() { Street street = new Street(); street.printAddress(); } public static void main(String[] args) { Town town = new Town(); town.createStreet(); Town.Street street1 = town.new Street(); Town.Street street2 = new Town().new Street(); street1.printAddress(); street2.printAddress(); } } www.examclouds.com
  6. 6. Способы создания внутреннего класса  Внутри метода внешнего класса, объект внутреннего класса создается как обычно: Street street = new Street();  Если мы создаем объект внутреннего класса не в методах внешнего класса или в статических методах внешнего класса, необходимо использовать объект внешнего класса: new Town().new Street(); or town.new Street(); www.examclouds.com
  7. 7. Ключевое слово this  Если необходимо получить ссылку на внутренний класс во внутреннем классе, используем слово this: System.out.println("Street is " + this);  Если необходимо получить ссылку на объект внешнего класса, запишите имя внешнего класса, за которым следует точка, а затем ключевое слово this: System.out.println("Town is " + Town.this); www.examclouds.com
  8. 8. Внутренний класс  Обычный внутренний класс является таким же членом внешнего класса, как и переменные и методы.  Следующие модификаторы могут быть применены к обычному внутреннему классу: o final o abstract o public o private o protected o static – но static преобразует его во вложенный класс o strictfp www.examclouds.com
  9. 9. Модификатор strictfp  Если метод описан как strictfp (явно либо неявно), то JVM гарантирует, что результаты вычисления выражений с double и float в пределах метода будут одинаковыми на всех платформах.  Модификатор strictfp для класса и интерфейса указывает на то, что все методы класса/интерфейса будут strictfp. www.examclouds.com
  10. 10. Задание 1. Создать класс User, содержащий private переменные login, password. 2. Создать внутренний класс Query в классе User. 3. Класс Query содержит метод printToLog(), который распечатывает на консоль сообщение о том что пользователь с таким то логином и паролем отправил запрос. 4. Класс User, содержит метод createQuery(), в котором создается объект класса Query и вызывается метод printToLog(). 5. В методе main(): o создать экземпляр класса User и вызвать метод createQuery(); o создать экземпляр класса Query и вызвать метод printToLog() используя конструкцию user.new Query(); o создать экземпляр класса Query и вызвать метод printToLog() используя конструкцию new User().new Query(); www.examclouds.com
  11. 11. Локальный класс  Локальные классы (local classes) определяются в блоке Java кода.  На практике чаще всего объявление происходит в методе некоторого другого класса.  Как и member классы, локальные классы ассоциируются с экземпляром внешнего класса и имеют доступ к его полям и методам.  Локальный класс может обращаться к локальным переменным и параметрам метода, если они объявлены с модификатором final или являются effective final (начиная с Java 8). www.examclouds.com
  12. 12. Effective final переменная  Effective final переменная это переменная, которая не объявлена явно как final, но ее значение не меняется.(Java 8) www.examclouds.com
  13. 13. Локальный класс  Экземпляр класса может быть создан внутри того же метода, что и класс, но ниже объявления класса.  Они не могут быть объявлены как private, public, protected или static.  Они не могут иметь внутри себя статических объявлений (полей, методов, классов). Исключением являются константы (static final).  Локальные классы могут быть объявлены как abstract или final. www.examclouds.com
  14. 14. Пример локального класса public class Town2 { private String postCode = "33333"; public void createAddress() { final int houseNumber = 34; class Street { public void printAddress() { System.out.println("PostCode is " + postCode); System.out.println("House Number is " + houseNumber); } } Street street = new Street(); street.printAddress(); } public static void main(String[] args) { Town2 town = new Town2(); town.createAddress(); } } www.examclouds.com
  15. 15. Локальный класс  Если локальный класс объявлен внутри статического метода, он имеет доступ только к статическим переменным класса. www.examclouds.com
  16. 16. Пример локального класса объявленного в статическом методе public class Town3 { private static String postCode = "33333"; public static void createAddress() { final int houseNumber = 34; class Street { public void printAddress() { System.out.println("PostCode is " + postCode); System.out.println("House Number is " + houseNumber); } } Street street = new Street(); street.printAddress(); } public static void main(String[] args) { Town3.createAddress(); } } www.examclouds.com
  17. 17. Задание  Переписать предыдущее задание, используя локальный класс. www.examclouds.com
  18. 18. Анонимный класс  Анонимный класс (anonymous class) - это локальный класс без имени.  Используется тогда, когда нужно переопределить метод класса или интерфейса.  Класс одновременно объявляется и инициализируется.  Они могут быть объявлены не только в методе, но и внутри аргумента метода. www.examclouds.com
  19. 19. Пример анонимного класса public class Potato { public void peel() { System.out.println("Чистим картошку."); } } public class Food { public static void main(String[] args) { Potato potato = new Potato() { @Override public void peel() { System.out.println("Чистим картошку в анонимном классе."); } }; potato.peel(); } } www.examclouds.com
  20. 20. Пример анонимного класса public class AnotherFood { public static void main(String[] args) { Potato potato = new Potato() { public void fry() { System.out.println("Жарим картошку в анонимном классе."); } @Override public void peel() { System.out.println("Чистим картошку в анонимном классе."); fry(); } }; potato.peel(); //Ошибка компиляции //potato.fry(); } }  Анонимный класс может не только переопределить методы класса наследника, но и добавить новые методы. Но новые методы НЕ могут быть вызваны извне анонимного класса. www.examclouds.com
  21. 21. Случаи использования анонимного класса  Тело класса является очень коротким.  Нужен только один экземпляр класса.  Класс используется в месте его создания или сразу после него.  Имя класса не важно и не облегчает понимание кода. www.examclouds.com
  22. 22. Пример анонимного класса расширяющего интерфейс import interfaces.Moveable; public class MoveableDemo { public static void main(String[] args) { Moveable moveable = new Moveable() { @Override public void moveRight() { System.out.println("MOVING RIGHT!!!"); } @Override public void moveLeft() { System.out.println("MOVING LEFT!!!"); } }; moveable.moveRight(); moveable.moveLeft(); } } www.examclouds.com
  23. 23. Задание  Создать анонимный класс расширяющий интерфейс Printable.  Вызвать его метод print(). www.examclouds.com
  24. 24. Статический вложенный класс  Статический вложенный класс (static nested class) – это внутренний класс объявленный с модификатором static.  Статический вложенный класс не имеет доступа к нестатическим полям и методам внешнего класса.  Доступ к нестатическим полям и методам может осуществляться только через ссылку на экземпляр внешнего класса. В этом плане static nested классы очень похожи на любые другие классы верхнего уровня. www.examclouds.com
  25. 25. Пример статического вложенного класса public class Town4 { public static class Street { public void go() { System.out.println("Go to the Street."); } } } public class City { public static class District { public void go() { System.out.println("Go to the District."); } } public static void main(String[] args) { Town4.Street street = new Town4.Street(); street.go(); District district = new District(); district.go(); } } www.examclouds.com
  26. 26. Задание  Переписать класс Query используя статический класс. www.examclouds.com
  27. 27. Пример матрицы  public class Matrix{ private int[] array; … } www.examclouds.com
  28. 28. Пример матрицы public class Matrix<T> { private T[] array; public Matrix(T[] array) { this.array = array.clone(); } public static void main(String[] args) { Matrix<Double> doubleMatrix = new Matrix<>(new Double[2]); Matrix<Integer> integerMatrix = new Matrix<>(new Integer[4]); Matrix<Byte> byteMatrix = new Matrix<>(new Byte[7]); } } www.examclouds.com
  29. 29. Что такое обобщения?  Обобщения - это параметризованные типы.  Параметризованные типы позволяют объявлять классы, интерфейсы и методы, где тип данных, которыми они оперируют, указан в виде параметра.  Используя обобщения, можно создать единственный класс, например, который будет автоматически работать с разными типами данных.  Классы, интерфейсы или методы, имеющие дело с параметризованными типами, называются обобщениями, обобщенными классами или обобщёнными методами.  Обобщения добавили в язык безопасность типов. www.examclouds.com
  30. 30. Ключевые моменты объявления класса  Matrix<Integer> integerMatrix - Integer является аргументом типа.  Java не создает разные версии класса Matrix или любого другого обобщенного класса. Имеется только одна версия класса Matrix, которая существует в прикладной программе.  Обобщения работают только с объектами! Gen<int> strOb =new Gen<int> (53) ; // Ошибка, нельзя использовать //примитивные типы www.examclouds.com
  31. 31. Ключевые моменты объявления класса  Т обозначает имя параметра типа.  Это имя используется в качестве заполнителя вместо которого в дальнейшем подставляется имя конкретного типа, передаваемого классу Matrix при создании объекта.  Это означает, что обозначение Т применяется в классе Matrix всякий раз, когда требуется параметр типа.  Всякий раз, когда объявляется параметр типа, он указывается в угловых скобках. www.examclouds.com
  32. 32. Ключевые моменты объявления класса Обобщенные типы отличаются в зависимости от типов-аргументов:  doubleMatrix = integerMatrix; // Не верно!  Несмотря на то, что doubleMatrix и integerMatrix имеют тип Matrix<T>, они являются ссылками на разные типы, потому что типы их параметров отличаются. www.examclouds.com
  33. 33. Обобщенный класс с двумя параметрами типа public class TwoGen<T, V> { private T obT; private V obV; public TwoGen(T obT, V obV) { this.obT = obT; this.obV = obV; } public void showTypes() { System.out.println("Тип T: " + obT.getClass().getName()); System.out.println("Тип V: " + obV.getClass().getName()); } public T getObT() { return obT; } public V getObV() { return obV; } } www.examclouds.com
  34. 34. Использование обобщенного класса с двумя параметрами типа public class SimpleGen { public static void main(String[] args) { TwoGen<Integer, String> twoGen = new TwoGen<>(88, "Generics"); twoGen.showTypes(); System.out.println("Значение T: " + twoGen.getObT()); System.out.println("Значение V: " + twoGen.getObV()); } } www.examclouds.com
  35. 35. Задание 1. Создать обобщенный класс с тремя параметрами (T, V, K). 2. Класс содержит три переменные типа (T, V, K). 3. Класс содержит конструктор, принимающий на вход параметры типа (T, V, K). 4. Класс содержит методы возвращающие значения трех переменных. 5. Создать метод, выводящий на консоль имена классов для трех переменных класса. www.examclouds.com
  36. 36. Ограниченные типы  Указывая параметр типа, можно наложить ограничение сверху в виде верхней границы, где объявляется суперкласс, от которого должны быть унаследованы все аргументы типов.  С этой целью вместе с параметром указывается ключевое слово extends: class Gen <Т extends Superclass>  Параметр типа Т может быть заменен только указанным суперклассом или его подклассами. www.examclouds.com
  37. 37. Пример использования ограниченного типа public class Average<T extends Number> { private T[] array; public Average(T[] array) { this.array = array; } public double average() { double sum = 0.0; for (T value : array) { sum += value.doubleValue(); } return sum / array.length; } } www.examclouds.com
  38. 38. Пример использования ограниченного типа public class AverageDemo { public static void main(String[] args) { Integer[] intArray = {1, 2, 3, 4, 5}; Average<Integer> integerAverage = new Average<>(intArray); System.out.println("Среднее значения для Integer " + integerAverage.average()); Double[] doubleArray = {1.1, 2.2, 3.3, 4.4, 5.5}; Average<Double> doubleAverage = new Average<>(doubleArray); System.out.println("Среднее значения для Double " + doubleAverage.average()); // Не откомпилируется, // потому что String не является наследником Number /* String[] strArray = {"1", "2", "3", "4", "5"}; Average<String> strAverage = new Average<>(strArray); System.out.println("Среднее значения для String “ + strAverage.average());*/ } } www.examclouds.com
  39. 39. Ключевые моменты использования ограниченного типа  В виде ограничения можно накладывать не только тип класса, но и тип интерфейса. public class MyClass<T extends Serializable> www.examclouds.com
  40. 40. Ключевые моменты использования ограниченного типа class Gen < T extends MyClass & MyInterface1 & MyInterface2> 1. Ограничение может включать в себя как тип класса, так и типы одного или нескольких интерфейсов. 2. Тип класса должен быть задан первым. 3. Накладывая на обобщенный тип ограничение, состоящее из класса и одного или нескольких интерфейсов, для их объединения следует воспользоваться логической операцией &: 4. Таким образом, любой тип, передаваемый параметру Т, должен быть подклассом, производным от класса MyClass и реализующим интерфейсы MyInterface1 и MyInterface2. www.examclouds.com
  41. 41. Задание  Наложить ограничения на параметры типа:  T должен реализовать интерфейс Comparable (классы оболочки, String),  V должен реализовать интерфейс Serializable и расширять класс Animal,  K должен расширять класс Number. www.examclouds.com
  42. 42. Применение метасимвольных аргументов Так как Average параметризованный тип, какой тип параметра вы укажете для Average, когда создадите параметр метода типа Average? Integer[] intArray = {1, 2, 3, 4, 5}; Average2<Integer> iob = new Average2<>(intArray); System.out.println("Среднее значения для Integer " + iob.average()); Double[] doubleArray = {1.1, 2.2, 3.3, 4.4, 5.5}; Average2<Double> dob = new Average2<>(doubleArray); System.out.println("Среднее значения для Double " + dob.average()); System.out.print("Средние значения для iob и dob "); if (iob.sameAvg(dob)) { System.out.println("одинаковые."); } else { System.out.println("разные."); } www.examclouds.com
  43. 43. Применение метасимвольных аргументов  !! Это не сработает! public boolean sameAvg(Average<T> ob) { return average() == ob.average(); } www.examclouds.com
  44. 44. Пример применения метасимвольного аргумента  Чтобы создать обобщенную версию метода sameAvg(), следует воспользоваться другим средством обобщений Jаvа – метасимвольным аргументом.  Метасимвольный аргумент обозначается знаком ? и представляет неизвестный тип.  Пример: boolean sameAvg(Average<?> ob) { return average() == ob.average(); } www.examclouds.com
  45. 45. Метасимвольный аргумент  Метасимвол не оказывает никакого влияния на тип создаваемых объектов класса Average. Это определяется оператором extends в объявлении класса Average.  Метасимвол просто совпадает c любым достоверным объектом класса Average. www.examclouds.com
  46. 46. Ограниченные метасимвольные аргументы  Метасимвольные аргументы могут быть ограничены почти таким же образом, как и параметры типов.  Ограничивать метасимвольный аргумент особенно важно при создании обобщенного типа, оперирующего иерархией классов. www.examclouds.com
  47. 47. Пример применения метасимвольного аргумента public class Average2<T extends Number> { private T[] array; public Average2(T[] array) { this.array = array.clone(); } public double average() { double sum = 0.0; for (T value : array) { sum += value.doubleValue(); } return sum / array.length; } public boolean sameAvg(Average2<?> ob) { return average() == ob.average(); } } www.examclouds.com
  48. 48. Пример применения метасимвольного аргумента public class AverageDemo2 { public static void main(String[] args) { Integer[] intArray = {1, 2, 3, 4, 5}; Average2<Integer> iob = new Average2<>(intArray); System.out.println("Среднее значения для Integer " + iob.average()); Double[] doubleArray = {1.1, 2.2, 3.3, 4.4, 5.5}; Average2<Double> dob = new Average2<>(doubleArray); System.out.println("Среднее значения для Double " + dob.average()); Float[] floatArray = {1.0F, 2.0F, 3.0F, 4.0F, 5.0F}; Average2<Float> fob = new Average2<>(floatArray); System.out.println("Среднее значения для Float " + fob.average()); System.out.print("Средние значения для iob и dob "); if (iob.sameAvg(dob)) { System.out.println("одинаковые."); } else { System.out.println("разные."); } System.out.print("Средние значения для iob и fob "); if (iob.sameAvg(fob)) { System.out.println("одинаковые."); } else { System.out.println("разные."); } } www.examclouds.com
  49. 49. Создание обобщенного метода  В методах обобщенного класса можно использовать параметр типа, а следовательно, они становятся обобщенными относительно параметра типа.  Но можно объявить обобщенный метод, в котором непосредственно используется один или несколько параметров типа.  Более того, можно объявить обобщенный метод, входящий в необобщенный класс. www.examclouds.com
  50. 50. Пример обобщенного метода public class GenMethodDemo { public static <T, V> boolean isIn(T x, V[] array) { for (V element : array) { if (x.equals(element)) { return true; } } return false; } public static void main(String[] args) { Integer[] intArray = {1, 2, 3, 4, 5}; if (isIn(2, intArray)) { System.out.println("2 входит в массив intArray"); } if (!isIn(7, intArray)) { System.out.println("7 не входит в intArray"); } System.out.println(); String[] strArray = {"one", "two", "three", "four", "five"}; if (isIn("two", strArray)) { System.out.println("two входит в массив strArray"); } if (!isIn("seven", strArray)) { System.out.println("seven не входит в массив strArray"); } } www.examclouds.com
  51. 51. Обобщенные конструкторы  Конструкторы также могут быть обобщенными, даже если их классы таковыми не являются. public class GenConstructor { private double value; public <T extends Number> GenConstructor(T arg) { value = arg.doubleValue(); } public void showValue() { System.out.println("value: " + value); } } public class GenConstructorDemo { public static void main(String[] args) { GenConstructor genConstructor1 = new GenConstructor(100); GenConstructor genConstructor2 = new GenConstructor(123.5F); genConstructor1.showValue(); genConstructor2.showValue(); } } www.examclouds.com
  52. 52. Обобщенные интерфейсы  В дополнение к обобщенным классам и методам вы можете объявлять обобщенные интерфейсы. Обобщенные интерфейсы специфицируются так же, как и обобщенные классы. public interface MyInterface<T> { T someMethod(T t); } public class MyClass<T> implements MyInterface<T> { @Override public T someMethod(T t) { return t; } public static void main(String[] args) { MyInterface<String> object = new MyClass<>(); String str = object.someMethod("some string"); } } www.examclouds.com
  53. 53. Иерархии обобщенных классов  Обобщенные классы могут быть частью иерархии классов так же, как и любые другие необобщенные классы.  То есть обобщенный класс может выступать в качестве суперкласса или подкласса.  Ключевое отличие между обобщенными и необобщенными иерархиями состоит в том, что в обобщенной иерархии любые аргументы типов, необходимые обобщенному суперклассу, всеми подклассами должны передаваться по иерархии вверх. www.examclouds.com
  54. 54. Иерархии обобщенных классов  Подкласс обобщенного суперкласса не обязательно должен быть обобщенным, но в нем все же должны быть, указаны параметры типа, требующиеся его обобщенному суперклассу.  Подкласс может, если требуется, быть, дополнен и своими параметрами типа.  Суперклассом для обобщенного класса может быть класс необобщенный. www.examclouds.com
  55. 55. Пример иерархии с обобщенным суперклассом public class GenericSuper<T> { private T ob; public GenericSuper(T ob) { this.ob = ob; } private T getOb() { return ob; } } public class GenericSub<T> extends GenericSuper<T> { public GenericSub(T ob) { super(ob); } } www.examclouds.com
  56. 56. Пример использования оператора instanceof с обобщенным типом public class HierarchyDemo { public static void main(String[] args) { GenericSuper<Integer> object = new GenericSub<>(88); if (object instanceof GenericSuper<?>) { System.out.println("object is instance of GenericSuper"); } if (object instanceof GenericSub<?>) { System.out.println("object is instance of GenericSub"); } // Ошибка компиляции - информация об обобщенном типе недоступна // во время выполнения /* if (object instanceof GenericSub<Integer>) { System.out.println("object is instance of GenericSub<Integer>"); }*/ } } www.examclouds.com
  57. 57. Некоторые ограничения присущие обобщениям public class GenRestriction<T> { private T ob; private T[] array; public GenRestriction(T ob, T[] array) { // Недопустимо!!! //оb = new Т(); //array = new Т[10]; this.ob = ob; this.array = array; } } 1. Нельзя создавать экземпляр по параметру типа. 2. Нельзя создать экземпляр массива, тип элемента которого определяется параметром типа. www.examclouds.com
  58. 58. Ограничения на обобщенные массивы  Нельзя создать массив специфических для типа обобщенных ссылок. public class GenArrays { public static void main(String[] args) { // Нельзя создать массив специфичных для типа обобщенных ссылок. // GenericSub<Integer>[] gens = new GenericSub<Integer>[10]; GenericSub<?>[] gens = new GenericSub<?>[10]; gens[0] = new GenericSub<>(34); } } www.examclouds.com
  59. 59. Ограничения на статические члены  Нельзя создавать обобщенные статические переменные и методы.  Но объявить статические обобщенные методы со своими параметрами типа все же можно. public class GenericWrongStatic<T> { // Неверно, нельзя создать статические переменные типа Т. //public static Т оb; // Неверно, ни один статический метод не может использовать Т. /* public static T getOb() { return оb; }*/ //Но объявить статические обобщенные методы со своими параметрами типа можно public static <V> void getOb(V v) { System.out.println(v); } } www.examclouds.com
  60. 60. • Лекции, задания, видео, тесты и вопросы на: • https://www.examclouds.com/ru/java/java-core- russian/lesson14 • Подписывайтесь на страницу: • https://www.facebook.com/Examclouds • Подписывайтесь на канал • https://www.youtube.com/c/tatyanamilkina www.examclouds.com

×