1. Введение в неизменные категории
Необычный класс: так называемый неизменный класс означает, что после создания экземпляра этого класса значение переменной его элемента не может быть изменено. Например, многие неизменные классы, которые поставляются с JDK: интернет, длинная и струнная и т. Д.
Переменные классы: по сравнению с неизменными классами, изменяемые классы могут изменить значения переменных членов после создания экземпляров. Большинство классов, созданных в разработке, принадлежат изменяемым классам.
2. Преимущества неизменных классов
После разговора о разнице между изменчивыми классами и неизменными классами, нам нужно дополнительно понять, почему существуют неизменные классы? Какие преимущества такая функция приносит Java?
1. Безопасность нити
Необываемые объекты защищены потоком и могут быть переданы между потоками. Нет необходимости использовать специальные механизмы для обеспечения задач синхронизации, поскольку значение объекта не может быть изменено. Это может уменьшить возможность параллельных ошибок, поскольку нет необходимости использовать некоторые механизмы блокировки для обеспечения задач согласованности памяти, что также снижает накладные расходы на синхронизацию.
2. Легко строить, использовать и проверять
3 ....
Необычный метод дизайна класса
Для дизайнерских непотимых классов я лично суммирую следующие принципы:
1. Добавьте последний модификатор в класс, чтобы убедиться, что класс не унаследован.
Если класс может быть унаследован, он разрушит механизм неизменности класса, пока класс наследования переопределяет методы родительского класса, а класс наследования может изменить значение переменной элемента, тогда, как только класс дочернего класса появляется в качестве родительского класса, нельзя гарантировать, что текущий класс изменен.
2. Убедитесь, что все переменные -члены должны быть частными, а окончательная модификация добавлена
Таким образом, гарантирует, что переменные -члены не имеют значения. Но этого недостаточно, потому что если это переменная элемента объекта, можно изменить его значение снаружи. Так что четвертый пункт компенсирует этот недостаток.
3. Методы не предоставляются для изменения переменных членов, включая сетевые
Избегайте изменения значения переменных членов через другие интерфейсы и разрушают неизменные функции.
4. Инициализируйте всех участников через конструктор и выполните глубокую копию (Deep Copy)
Если объект, передаваемый конструктором, напрямую назначается переменной элемента, он все равно может быть изменен путем изменения входящего объекта, что приведет к изменению значения внутренней переменной. Например:
публичный финальный класс ImmutabledEmo {private final int [] myarray; public immutabledemo (int [] array) {this.myarray = array; // неправильный } }Этот метод не может гарантировать неизменность. Myarray и массив указывают на тот же адрес памяти. Пользователи могут изменить значение внутри Myarray, изменяя значение объекта массива за пределами Immutabledemo.
Чтобы убедиться, что внутреннее значение не будет изменено, глубинная копия может использоваться для создания новой памяти для сохранения входящего значения. Правильный способ сделать это:
открытый финальный класс myimtabledemo {private final int [] myarray; public myimutabledemo (int [] array) {this.myarray = array.clone (); }}5. В методе Getter не возвращайте сам объект напрямую, но клонируйте объект и возвращайте копию объекта.
Этот подход также предотвращает утечку объекта и предотвращает прямую работу переменных элементов после получения внутренних изменяемых объектов -членов через Getters, что приводит к изменениям в переменных члена.
IV Неизменность строковых объектов
Строковой объект не может быть изменен после создания памяти. Создание неизменных объектов обычно соответствует вышеуказанным принципам. Давайте посмотрим, как реализован строковый код.
Public Final Class StringImplomements java.io.serializable, сопоставимый <string>, charequestence {/** Значение используется для хранения символов. */private final vical gar [];/** Смещение является первым индексом используемого хранилища. */private final int offset;/** Подсчет - это количество символов в строке. */private final int count;/** кэшировать хэш -код для строки*/private int hash; // по умолчанию к 0..public String (char value []) {this.value = arrays.copyof (value, value.length); // Операция глубокой копии} ... public char [] toCharraray () {// не может использовать Arrays.copyOf из -за заказа инициализации класса.Как показано в приведенном выше коде, можно наблюдать следующие детали проекта:
1. Класс Стрига модифицируется окончательным и не может быть унаследован
2. Все члены строки установлены как частные переменные
3. Установителя значений не существует
4. и установите значение и смещено на окончательный.
5. При передаче значения массива переменных [] скопируйте его вместо копирования значения [] непосредственно во внутреннюю переменную.
6. При получении значения он не возвращает ссылку на объект, но возвращает копию объекта.
Это согласуется с характеристиками инвариантного типа, обобщенных выше, а также гарантирует, что тип строки является неизменным классом.
5. Преимущества и недостатки неизменности строковых объектов
Из предыдущего анализа раздела строковые данные неизменны, так каковы преимущества настройки такой функции? Я суммировал это следующим образом:
1. Требования к постоянным бассейнам строк.
Постоянные бассейны строки могут повторно использовать некоторые константы символов в постоянном бассейне, избегая воссоздания одного и того же объекта каждый раз и экономит место для хранения. Но если строка является переменной, строка одного и того же содержимого также указывает на одно и то же пространство памяти постоянного пула. Когда переменная изменяет значение этой памяти, другие обходные значения также изменятся. Следовательно, это не соответствует первоначальному намерению постоянного дизайна пула.
2. Соображения безопасности потока.
Один и тот же экземпляр строки может быть использован несколькими потоками. Таким образом, нет необходимости использовать синхронизацию из -за проблем безопасности потока. Строки защищены нитью.
3. Классовые погрузчики должны использовать строки, а неизменность обеспечивает безопасность так, чтобы правильный класс был загружен. Например, если вы хотите загрузить класс java.sql.connection, и это значение изменяется на Myhacked.connection, оно приведет к неизвестному повреждению вашей базы данных.
4. Поддержка хэш -картирования и кэширование.
Поскольку строки неизменны, хэшкод кэшируется при его создании и не нужно пересчитываться. Это делает строки очень подходящими в качестве ключей в карте, а скорость обработки строк быстрее, чем другие ключевые объекты. Вот почему ключи в HashMap часто используют струны.
недостаток:
1. Если необходимо изменить значение объекта строки, будет создано большое количество строковых объектов.
6. Действительно ли объект строки неизменным?
Хотя объект String устанавливает значение в конечном счете, он также гарантирует, что его переменные -элементы не имеют отношения к различным механизмам. Тем не менее, это все еще может быть изменено с помощью механизма отражения. Например:
// Создать строку «Hello World» и назначить ее на ссылку SString S = "Hello World"; System.out.println ("s =" + s); // hello world // Получить поле значения в поле Строка класса valuefieldofstring = string.class.getdeclaredfield ("value"); // Изменение разрешения доступа атрибута значения valuefilefstring.setAccessible (true); // Получить значение атрибута значения на объектном объекте [] value = (char] valuefordefstring.get (s); = '_'; System.out.println ("s =" + s); //Привет, мирРезультат печати:
S = Hello Worlds = hello_world
Было обнаружено, что значение строки изменилось. То есть так называемый «неподвижный» объект может быть изменен с помощью отражения.
Суммировать
Неизримым классом является значение обхода элемента, которое не может быть изменено после создания экземпляра. Эта функция позволяет неизменным классам предоставлять функции безопасных потоков, но также приносит накладные расходы создания объектов. Каждое изменение атрибута - воссоздать новый объект. JDK также предоставляет много неизменных классов, таких как целое число, двойная, строка и т. Д. Необвисываемые характеристики строки в основном для удовлетворения потребностей постоянного объединения, безопасности потоков и загрузки класса. Рациональное использование неизменных классов может принести большие преимущества.
Вышеуказанное является неизменным механизмом Java (неизменной) и неизменностью строки (рекомендуется), введенной вам редактором. Я надеюсь, что это будет полезно для вас. Если у вас есть какие -либо вопросы, пожалуйста, оставьте мне сообщение, и редактор ответит вам вовремя. Большое спасибо за вашу поддержку сайту wulin.com!