Перевод «protected» на русский
Одна из теорий утверждает, что это происходит из-за того, что женщины каким-то образом защищены от аутизма.
The judges themselves are also protected from any political interference.
Что касается самих судей, то они также защищены от любого политического вмешательства.
Foreign workers are also protected against racially-motivated termination of their employment contract.
Иностранные трудящиеся в равной степени защищены от произвольного расторжения трудового договора по мотивам расовой дискриминации.
Share Password protected files through public links with expiration date.
Предоставление файлов, защищенных паролем, по общедоступным ссылкам с датой истечения срока действия.
This suggests that people were still protected from Ebola 40 years later.
Это говорит о том, что люди и спустя 40 лет по-прежнему были защищены от Эболы.
Ironically, Freud was protected from asphyxia at birth.
Как ни странно, Фрейд был защищен от асфиксии при рождении.
The company says partners following Facebook «best practices» were automatically protected.
Компания заявляет, что партнеры, следующие за Facebook, «лучшие практики» были автоматически защищены.
The Cave and Basin wasn’t really protected.
Порт и береговой посёлок, по существу, не были серьёзно защищены.
Возможно неприемлемое содержание
Примеры предназначены только для помощи в переводе искомых слов и выражений в различных контекстах. Мы не выбираем и не утверждаем примеры, и они могут содержать неприемлемые слова или идеи. Пожалуйста, сообщайте нам о примерах, которые, на Ваш взгляд, необходимо исправить или удалить. Грубые или разговорные переводы обычно отмечены красным или оранжевым цветом.
Методы доступа. Наиболее популярные ситуации
Статья в первую очередь расчитана на начинающих разработчиков, либо для тех, кто только начинает переходить от процедурного стиля программирования к ООП, посему матерых гуру просьба не вгонять в минуса 🙂
Права доступа к свойствам и методам — это на первый взгляд всего лишь три слова: private, protected и public. Но что скрывается за ними? Какие преимущества это дает в разработке? И как их правильно использовать? Здесь, как и во всех других аспектах программирования, без практики не разобраться…
Одна из трех основных концепций ООП — наследование (другие две: инкапсуляция и полиморфизм). Вобщем-то именно для нее и были реализованы права доступов. Основанная идея наследования: Дочерний объект, при наследовании (extend) родителя перенимает себе все родительские методы и свойства, а так же может обзавестись своими собственными. Понимая эту базу, можно перейти в всему что находится ниже…
Private — объявляет метод или свойство доступным только в том классе в котором он присутствует. Тоесть к private методам и свойствам мы не можем обращаться ни из объектов, ни из дочерних классов.
Protected — объявляет метод или свойство защищенными. Тоесть такими, которые не могут быть доступны из объекта, реализующего класс, но вполне может быть использовано в дочерних классах.
Public — публичный. Классы и методы, объявленные public, могут быть доступны как внутри самого класса, так и в дочерних классах и в объектах, реализовавших класс.
Сразу хочу заметить, что при наследовании, методы доступа изменяться могут только к более лояльным. тоесть в следующей последовательности, но не обратно: private → protected → public
Так же методы могут быть final тоесть такими, которые невозможно переопределить в классах потомках.
Вобщем-то все методы доступа используются исключительно для самодокументации кода и не несут никакой логической составляющей, так что и без них жизнь только тяжела, но не невозможна, что доказывает РНР4, в котором все методы и свойства были публичными…
Практика
Иногда случаются ситуации, когда этих методов доступа недостаточно. Тоесть, например, мы можем хотеть иметь доступ из объекта на чтение какого-то свойства, но при этом не иметь возможности в него писать. Самое простое решение: объявить свойство public и добавить комментарий /* только для чтения */, но про комментарий можно ненароком забыть и испортить логику поведения программы, вклинившись с нестандартным значением посреди выполнения. тогда приходит время использовать геттеры (getter\’s). Геттер — не что иное, как метод класса, реализующий исключительную возможность читать не публичные свойства из объекта. Вот пример:
class A private $a = 7;//мы не можем читать и писать в это свойство из объекта, реализующего этот класс
public function getA() < //публичный метод будет доступен объекту для обращения
return $this->a; //внутри класса мы можем получать доступ к приватным свойствам
>
>
$obj = new A();
echo $obj->getA();//мы получили значение приватной переменной $a
Похожим способом ведут себя и сеттеры (setter\’s), когда нам необходимо иметь возможность установить значение переменной, но не читать ее напрямую, так как она, к примеру, должна быть преобразована прежде чем быть использованной. Пример метода сеттера:
//.
public funtion setA($value) < //метод будет доступен для объекта
$this->a = $value; //приватное свойство $a может быть установленное внутри класса, но не доступно для прямого влияния из объекта
>
//.
Еще одним вариантом реализации доступа к методам, когда метод должен быть отовсюду доступен только для чтения, является введение \«псевдо-свойства\»:
class A public function getValue() static $value;
if (empty($value)) $value = //. тут значение создается по каким-то известным параметрам и повлиять извне на него мы никак не сможем
>
в примере выше, класс А будет обладать псевдо-свойством $value. Псевдо — потому что оно реализуется исключительно через метод, а доступ к нему возможен только на чтение. Еще можете заметить что я использовал паттерн \«ленивой инициализации\», что бы отложить создание свойства до последнего момента и заодно как бы \«закешировать\» его. Где это можно применить, хорошо проиллюстрировано в соседнем топике об ООП в РНР.
Хорошей практикой является сокрытие всех свойств методом private и, в зависимости от нужд, создавать для них сеттеры или геттеры, но нужно быть внимательным, что если для свойства существует и сеттер и геттер, а дополнительной логики обработки данных нет, то не проще ли их убрать, а свойство сделать публичным? 🙂
Область видимости
Область видимости свойства или метода может быть определена путем использования следующих ключевых слов в объявлении: public, protected или private. Доступ к свойствам и методам класса, объявленным как public (общедоступный), разрешен отовсюду. Модификатор protected (защищенный) разрешает доступ наследуемым и родительским классам. Модификатор private (закрытый) ограничивает область видимости так, что только класс, где объявлен сам элемент, имеет к нему доступ.
Область видимости свойства
Свойства класса должны быть определены через модификаторы public, private, или protected. Если же свойство определено с помощью var, то оно будет доступно как public свойство.
Пример #1 Объявление свойства класса
/**
* Определение MyClass
*/
class MyClass
public $public = ‘Общий’ ;
protected $protected = ‘Защищенный’ ;
private $private = ‘Закрытый’ ;
?php
function printHello ()
echo $this -> public ;
echo $this -> protected ;
echo $this -> private ;
>
>
$obj = new MyClass ();
echo $obj -> public ; // Работает
echo $obj -> protected ; // Неисправимая ошибка
echo $obj -> private ; // Неисправимая ошибка
$obj -> printHello (); // Выводит Общий, Защищенный и Закрытый
/**
* Определение MyClass2
*/
class MyClass2 extends MyClass
// Мы можем переопределить public и protected методы, но не private
protected $protected = ‘Защищенный2’ ;
function printHello ()
echo $this -> public ;
echo $this -> protected ;
echo $this -> private ;
>
>
$obj2 = new MyClass2 ();
echo $obj2 -> public ; // Работает
echo $obj2 -> protected ; // Неисправимая ошибка
echo $obj2 -> private ; // Неопределен
$obj2 -> printHello (); // Выводит Общий, Защищенный2 и Неопределен
Замечание: Метод объявления переменной через ключевое слово var, принятый в PHP 4, до сих пор поддерживается в целях совместимости (как синоним ключевого слова public). В версиях PHP 5 ниже 5.1.3 такое использование выводит предупреждение E_STRICT .
Область видимости метода
Методы класса должны быть определены через модификаторы public, private, или protected. Методы, где определение модификатора отсутствует, определяются как public.
Пример #2 Объявление метода
/**
* Определение MyClass
*/
class MyClass
// Объявление общедоступного конструктора
public function __construct ()?php
// Объявление общедоступного метода
public function MyPublic ()
// Объявление защищенного метода
protected function MyProtected ()
// Объявление закрытого метода
private function MyPrivate ()
// Это общедоступный метод
function Foo ()
$this -> MyPublic ();
$this -> MyProtected ();
$this -> MyPrivate ();
>
>
$myclass = new MyClass ;
$myclass -> MyPublic (); // Работает
$myclass -> MyProtected (); // Неисправимая ошибка
$myclass -> MyPrivate (); // Неисправимая ошибка
$myclass -> Foo (); // Работает общий, защищенный и закрытый
/**
* Определение MyClass2
*/
class MyClass2 extends MyClass
// Это общедоступный метод
function Foo2 ()
$this -> MyPublic ();
$this -> MyProtected ();
$this -> MyPrivate (); // Неисправимая ошибка
>
>
$myclass2 = new MyClass2 ;
$myclass2 -> MyPublic (); // Работает
$myclass2 -> Foo2 (); // Работает общий и защищенный, закрытый не работает
class Bar
public function test () $this -> testPrivate ();
$this -> testPublic ();
>
public function testPublic () echo «Bar::testPublic\n» ;
>
private function testPrivate () echo «Bar::testPrivate\n» ;
>
>
class Foo extends Bar
public function testPublic () echo «Foo::testPublic\n» ;
>
private function testPrivate () echo «Foo::testPrivate\n» ;
>
>
$myFoo = new foo ();
$myFoo -> test (); // Bar::testPrivate
// Foo::testPublic
?>
Видимость из других объектов
Объекты одного типа имеют доступ к элементам с модификаторами private и protected друг друга, даже если не являются одним и тем же экземпляром. Это объясняется тем, что реализация видимости элементов известна внутри этих объектов.
Пример #3 Доступ к элементам с модификатором private из объектов одного типа
public function __construct ( $foo )
$this -> foo = $foo ;
>
private function bar ()
echo ‘Доступ к закрытому методу.’ ;
>
public function baz ( Test $other )
// Мы можем изменить закрытое свойство:
$other -> foo = ‘hello’ ;
var_dump ( $other -> foo );
// Мы также можем вызвать закрытый метод:
$other -> bar ();
>
>
$test = new Test ( ‘test’ );
$test -> baz (new Test ( ‘other’ ));
?>
Результат выполнения данного примера:
string(5) "hello" Доступ к закрытому методу.
Что означает protected
Все члены класса в языке Java — поля и методы — имеют модификаторы доступа. В прошлых темах мы уже сталкивались с модификатором public . Модификаторы доступа позволяют задать допустимую область видимости для членов класса, то есть контекст, в котором можно употреблять данную переменную или метод.
В Java используются следующие модификаторы доступа:
- public : публичный, общедоступный класс или член класса. Поля и методы, объявленные с модификатором public, видны другим классам из текущего пакета и из внешних пакетов.
- private : закрытый класс или член класса, противоположность модификатору public. Закрытый класс или член класса доступен только из кода в том же классе.
- protected : такой класс или член класса доступен из любого места в текущем классе или пакете или в производных классах, даже если они находятся в других пакетах
- Модификатор по умолчанию . Отсутствие модификатора у поля или метода класса предполагает применение к нему модификатора по умолчанию. Такие поля или методы видны всем классам в текущем пакете.
Рассмотрим модификаторы доступа на примере следующей программы:
public class Program < public static void main(String[] args) < Person kate = new Person("Kate", 32, "Baker Street", "+12334567"); kate.displayName(); // норм, метод public kate.displayAge(); // норм, метод имеет модификатор по умолчанию kate.displayPhone(); // норм, метод protected //kate.displayAddress(); // ! Ошибка, метод private System.out.println(kate.name); // норм, модификатор по умолчанию System.out.println(kate.address); // норм, модификатор public System.out.println(kate.age); // норм, модификатор protected //System.out.println(kate.phone); // ! Ошибка, модификатор private >> class Person < String name; protected int age; public String address; private String phone; public Person(String name, int age, String address, String phone)< this.name = name; this.age = age; this.address = address; this.phone = phone; >public void displayName() < System.out.printf("Name: %s \n", name); >void displayAge() < System.out.printf("Age: %d \n", age); >private void displayAddress() < System.out.printf("Address: %s \n", address); >protected void displayPhone()< System.out.printf("Phone: %s \n", phone); >>
В данном случае оба класса расположены в одном пакете — пакете по умолчанию, поэтому в классе Program мы можем использовать все методы и переменные класса Person, которые имеют модификатор по умолчанию, public и protected. А поля и методы с модификатором private в классе Program не будут доступны.
Если бы класс Program располагался бы в другом пакете, то ему были бы доступны только поля и методы с модификатором public.
Модификатор доступа должен предшествовать остальной части определения переменной или метода.
Инкапсуляция
Казалось бы, почему бы не объявить все переменные и методы с модификатором public , чтобы они были доступны в любой точке программы вне зависимости от пакета или класса? Возьмем, например, поле age, которое представляет возраст. Если другой класс имеет прямой доступ к этому полю, то есть вероятность, что в процессе работы программы ему будет передано некорректное значение, например, отрицательное число. Подобное изменение данных не является желательным. Либо же мы хотим, чтобы некоторые данные были достуны напрямую, чтобы их можно было вывести на консоль или просто узнать их значение. В этой связи рекомендуется как можно больше ограничивать доступ к данным, чтобы защитить их от нежелательного доступа извне (как для получения значения, так и для его изменения). Использование различных модификаторов гарантирует, что данные не будут искажены или изменены не надлежащим образом. Подобное сокрытие данных внутри некоторой области видимости называется инкапсуляцией .
Так, как правило, вместо непосредственного применения полей используют методы доступа. Например:
public class Program < public static void main(String[] args) < Person kate = new Person("Kate", 30); System.out.println(kate.getAge()); // 30 kate.setAge(33); System.out.println(kate.getAge()); // 33 kate.setAge(123450); System.out.println(kate.getAge()); // 33 >> class Person < private String name; private int age = 1; public Person(String name, int age)< setName(name); setAge(age); >public String getName() < return this.name; >public void setName(String name) < this.name = name; >public int getAge() < return this.age; >public void setAge(int age) < if(age >0 && age < 110) this.age = age; >>
И затем вместо непосредственной работы с полями name и age в классе Person мы будем работать с методами, которые устанавливают и возвращают значения этих полей. Методы setName, setAge и наподобие еще называют мьютейтерами (mutator), так как они изменяют значения поля. А методы getName, getAge и наподобие называют аксессерами (accessor), так как с их помощью мы получаем значение поля.
Причем в эти методы мы можем вложить дополнительную логику. Например, в данном случае при изменении возраста производится проверка, насколько соответствует новое значение допустимому диапазону.