ОО-абстракция возникает во время проектирования на уровне класса с цель сокрытия сложности реализации в том, как функции, предлагаемые API / дизайном / системой, были реализованы, в некотором смысле упрощая "интерфейс" для доступа к базовой реализации. .
Процесс абстракции может повторяться на все более «более высоких» уровнях (слоях) классов, что позволяет строить большие системы без увеличения сложности кода и понимания на каждом уровне.
Например, разработчик Java может использовать высокоуровневые функции FileInputStream, не беспокоясь о том, как это работает (т.е. дескрипторы файлов, проверки безопасности файловой системы, выделение памяти и буферизация будут управляться изнутри и скрыты от потребителей). Это позволяет изменять реализацию FileInputStream
, и пока API (интерфейс) для FileInputStream
остается согласованным, код, созданный для предыдущих версий, будет работать.
Точно так же при разработке собственных классов вы захотите по возможности скрыть детали внутренней реализации от других.
В определении Буча 1 объектно-ориентированная инкапсуляция достигается с помощью Скрытие информации, в частности, для сокрытия внутренних данных (полей / членов, представляющих состояние), принадлежащих экземпляру класса, путем обеспечения доступа к внутренним данным в контролируемым образом, и предотвращение прямого внешнего изменения этих полей, а также сокрытие любых внутренних методов реализации класса (например, путем их приватности).
Например, поля класса могут быть сделаны private
по умолчанию, и только если требуется внешний доступ к ним, get()
и / или set()
(или Property
) будут доступны из класса. (В современных ОО-языках поля могут быть помечены как readonly
/ final
/ immutable
, что дополнительно ограничивает изменение, даже внутри класса).
Пример, когда НЕ применялось сокрытие информации (Плохая практика):
class Foo {
// BAD - NOT Encapsulated - code external to the class can change this field directly
// Class Foo has no control over the range of values which could be set.
public int notEncapsulated;
}
Пример применения инкапсуляции полей:
class Bar {
// Improvement - access restricted only to this class
private int encapsulatedPercentageField;
// The state of Bar (and its fields) can now be changed in a controlled manner
public void setEncapsulatedField(int percentageValue) {
if (percentageValue >= 0 && percentageValue <= 100) {
encapsulatedPercentageField = percentageValue;
}
// else throw ... out of range
}
}
Пример неизменяемой инициализации поля или только для конструктора:
class Baz {
private final int immutableField;
public void Baz(int onlyValue) {
// ... As above, can also check that onlyValue is valid
immutableField = onlyValue;
}
// Further change of `immutableField` outside of the constructor is NOT permitted, even within the same class
}
Re: абстракция против абстрактного класса
Абстрактные классы - это классы, которые способствуют повторному использованию общности между классами, но сами по себе не могут быть созданы напрямую с помощью new()
- абстрактные классы должны быть подклассами, и могут быть созданы только concrete
(не абстрактные) подклассы. Возможно, одним из источников путаницы между Abstraction
и abstract class
было то, что на заре OO наследование более активно использовалось для повторного использования кода (например, со связанными абстрактными базовыми классами). В настоящее время композиция обычно предпочтительнее наследования, и для достижения абстракции доступно больше инструментов, например через интерфейсы, события / делегаты / функции, трейты / миксины и т. д.
Re: инкапсуляция против сокрытия информации
Значение инкапсуляции со временем изменилось, и в последнее время _ 17_ может также использоваться в более общем смысле при определении того, какие методы, поля, свойства, события и т. д. необходимо объединить в класс.
Цитата из Википедии:
В более конкретной настройке объектно-ориентированного языка программирования это понятие используется для обозначения либо механизма сокрытия информации, либо механизма связывания, либо их комбинации.
Например, в заявлении
Я инкапсулировал код доступа к данным в отдельный класс
.. интерпретация инкапсуляции примерно эквивалентна разделению проблем или Единого ответственного лица («S» в SOLID), и, возможно, может использоваться в качестве синоним рефакторинга.
[1] После того, как вы увидели изображение кота инкапсуляции, вы никогда не забудете инкапсуляцию - стр. 46 книги" Объектно-ориентированный анализ и дизайн с приложениями ", 2-е изд.
person
StuartLC
schedule
15.08.2012