В прошлом уроке мы рассмотрели базовые принципы инкапсуляции. Теперь, продолжая эту тему, пора познакомиться с модификаторами доступаpublic и private.
С их помощью можно ограничивать доступ к определённым элементам класса — например, полям и методам.
Если вспомнить пример из предидущего урока, то в классе Cat перед полями String name и String color не было указано никаких модификаторов. Однако, по умолчанию они являются public, что означает открытый доступ.
Благодаря этому мы могли напрямую через объекткота записать значения в его поля name и color вот так – somecat.name = “Barsik” и somecat.color = “White”.
Если мы поставим перед этими полями private, то это уже будет запрещено.
С полями класса помеченными как private можно работать только в пределах класса, то есть, например, в пределах методов или конструкторов этого класса.
Поясним на примере:
class Cat {
// пусть name будет public, а color будет private
public String name;
private String color;
Cat(String catColor) {
color = catColor;
// к color можно обращаться только
// в пределах класса кошки и ниоткуда больше.
// Например, ниже обращаемся к color
// в конструкторе класса кошки для вывода
// содержимого этого приватного поля на консоль.
System.out.println(color);
}
void sayMeow() {
System.out.println(“Meow”);
}
}
class Modifiers {
public static void main(String[] args) {
Cat somecat = new Cat(“White”);
// name помечен как public, поэтому мы можем
// напрямую через объект записать
// в него значение “Barsik”.
somecat.name = “Barsik”;
System.out.println(somecat.name);
// Если мы раскомментируем строчку кода ниже
// то будет ошибка, так как color помечен как private.
// somecat.color = “White”;
// То есть опять-таки, к private полям можно
// обращаться только в пределах класса.
}
}
Вывод:
Все эти модификаторы также можно применять к методам класса, конструкторам и самим классам — с той же целью: ограничить доступ к внутренним элементам класса извне.
ООП основывается на трёх ключевых принципах: – Инкапсуляция, Полиморфизм, Наследование.
Начнем с инкапсуляции.
Инкапсуляция означает сокрытие деталей реализации класса от внешнего кода, который просто использует этот класс.
Это означает, что тому, кто создал объект класса и пользуется им, совсем не обязательно знать его внутреннюю реализацию — достаточно понимания доступных методов и правил их использования. То есть можно работать с полями и методами объекта, даже не видя сам класс, из которого он создан.
Если вспомнить пример из прошлого урока про кошку, то тому кто создал и пользуется классом кошки не обязательно видеть класс кошки.
Также инкапсуляция значит защиту внутренних данных класса от другого кода, никак не относящемуся к данному классу.
То есть, например, класс кошки не должен иметь доступ к полям класса собаки, это разные животные, поэтому то мы и отделили их в разные классы, чтобы у них был ограниченный доступ друг к другу.
Простейший пример базовой инкапсуляции:
class Cat{
String name;
String color;
Cat (String catName, String catColor) {
name = catName;
color = catColor;
}
void sayMeow(){
System.out.println(“Meow”);
}
}
class Dog {
//Отсюда классу Dog не доступны поля кошки name и color,
//а также метод sayMeow. То есть в этом классе нельзя
//использовать содержимое класса Cat.
String name;
String color;
Dog (String dogName, String dogColor) {
name = dogName;
color = dogColor;
}
void sayWuf(){
System.out.println(“Wuf”);
}
}
class Incapsulation {
public static void main(String[] args) {
Cat somecat = new Cat(“Barsik”, “White”);
System.out.println(somecat.name);
}
}
Это был бызовый пример инкапсуляции, но под инкапсуляцией также, конечно, имеют ввиду модификаторы доступа и свойства (геттеры, сеттеры), которые будут рассмотрены в следующих уроках.
У класса может быть специальный метод, который не имеет возвращаемого значения и который имеет то же самое имя, что и класс.
Этот метод называется конструктором.
Он нужен чтобы при создании объектаклассаможно было выполнить какие-то действия — например, сразу при создании объекта присвоить его полям значения.
class Cat{
String name;
String color;
// Видим, что перед Cat ничего не указано —
// это значит, что этот метод это точно констурктор
// и что он не возвращает накакого значения.
// При создании объекта класса
// в конструктор будут передаваться
// два строковых значения — имя кошки и её цвет.
Cat (String catName, String catColor) {
// И эти переданные значения
// присваиваются полям name и color объекта.
name = catName;
color = catColor;
}
void sayMeow(){
System.out.println(“Meow”);
}
}
// Класс с методом main, где создаётся объект кота.
class Constructors{
public static void main(String[] args) {
// Очевидно, что ниже после new вызываеться
// конструктор, который мы определили выше.
// Через него создаваемому объекту кошки
// задаеться имя и цвет.
Cat somecat = new Cat(“Barsik”, “White”);
// Таким образом в конструкторе
// мы можем выполнять какие-либо действия
// сразу при создании объекта.
// Например, присвоить
// полям объекта значения.
// Выведем на консоль установленное
// в конструкторе имя кошки.
System.out.println(somecat.name);
}
}
Вывод:
На самом деле, мы уже сталкивались с конструктором в прошлом уроке когда создавали объект кота вот так:
Cat somecat = new Cat();.
В данном случае это конструктор по умолчанию, который автоматически создаётся компилятором, если в классе не определён ни один другой. Он позволяет создавать объекты без параметров. Однако если мы явно добавим свой конструктор (например, с параметрами), компилятор уже не создаст конструктор по умолчанию — его придётся прописать вручную.
ООП (Объектно-ориентированное программирование) – это способ построения программных продуктов. Такие программные продукты состоят из объектов и вся работа такого программного продукта построена на взаимодействии этих объектов.
Что же такое объект в таком программном продукте?
Да, в общем-то, всё что угодно.
Например, какой-либо элемент интерфейса – скажем, панель с кнопками – может быть обьектом.
Или если, например, программный продукт как-то связан с котами (например, программа для поиска подходящей породы кошки), то в ней точно будет объект кота.
И таких разных объектов в продукте может быть очень много и все они будут тем или иным образом взаимодействовать друг с другом.
То есть, как уже можно было догадаться, объект – это программная модель какой-либо сущности реального мира.
Сущность на основе которой строиться модель может иметь какие-либо характеристики и может проявлять какое-либо поведение. Соответственно модель тоже должна содержать эти характеристики и уметь проявлять поведение этой сущности.
Характеристики в объекте правильно называть свойствами, а какое-либо поведение объект проявляет с помощью методов(функций) в нем.
Например, есть сущность реального мира кот. Кот имеет характеристики – имя кота, цвет кота и т.д.
Кот может проявлять какое-либо поведение – например сказать Мяу.
Если представить кота, как его модель в виде объекта, то свойствами этого объекта будут, например, кот по имени Барсик серого цвета, и он будет говорить мяу с помощью метода в нем.
Как видим, объект кота уже имеет конкретное имя Барсик и имеет конкретный цветсерый. То есть объект – это уже конкретный кот, а не просто кот в общем.
А вот кот в общем – это КЛАСС.
Кот в общем – это шаблонпо которому был создан объект кота.
То есть классзадает, что у кота должно быть имя и цвет (это называется ПОЛЯМИ класса) и он должен уметь говорить мяу (в классеописывается то, как он должен говорить мяу).
А уже по этому шаблонусоздается объект кота с конкретным именем, цветом и он уже, собственно, говорит мяу, как ему было задано говорить мяу в классе кота.
Класс кота и объект этого класса на примере.
Ниже приведен класс кота и создание его объекта с подробным пояснением.
// Это класс кота (кот “в общем” или шаблон кота).
class Cat {
// Это поля класса. То есть любой кот, который будет создан по этому шаблону, будет иметь
// имя и цвет. Когда по шаблону кота будет создан конкретный объект кота,
// этот объект будет иметь конкретное значение в name и конкретное значение в color.
String name;
String color;
// Любой кот должен уметь говорить “мяу”.
// Здесь в методе sayMeow мы описываем, как наш кот будет говорить “мяу”.
void sayMeow() {
System.out.println(“Meow”);
}
}
class JavaOOP {
public static void main(String[] args) {
// В main мы создаем объект кошки по классу кошки.
// То есть мы создаем конкретного кота.
// С помощью new выделяем память под объект этого кота.
Cat somecat = new Cat();
// Внизу мы даем этому конкретному коту имя и цвет.
somecat.name = “Barsik”;
somecat.color = “White”;
// И теперь давайте же наш только что появившийся кот скажет “мяу”.
somecat.sayMeow();
}
}