Какими методами настраивается сериализация?
Интерфейс Serializable пуст, но есть ряд методов, добавив которые в сериализуемый класс можно добиться изменения этапов процесса сериализации и десериализации.
readObjectNoData() используется для инициализации класса-родителя, который при сериализации оригинального объекта еще не был родителем. Подробное объяснение.
readObject(ObjectInputStream s) переопределяет стандартную десериализацию.
Методы readObject* похожи на конструктор. Как и конструктор, они подвержены проблеме виртуального вызова. Как и конструктор, они используются для поддержания инвариантов класса (только для случая десериализации).
writeObject(ObjectOutputStream s) используется для записи собственной сериализационной формы.
Object readResolve() может использоваться для реализации какого-либо порождающего паттерна при десериализации. Даже при его использовании объект сначала будет десериализован, поэтому рекомендуется вместе с этим методом помечать все поля transient. Видимость этого метода для наследника определяет, будет ли наследник вызывать его.
Для подмены объекта при записи добавляется симметричный метод Object writeReplace().
Интерфейс Externalizable дает инструмент полной подмены реализации сериализации. Рассмотрим его в следующих постах.
#Сериализация
Зачем используется Serial Version UID? Что если не определить его?
Сериализуемый класс явно или неявно, но всегда имеет serialVersionUID. Это число типа long, которое представляет собой «версию» сериализационной формы класса. Если при сериализации/десериализации значения serialVersionUID не совпадают – будет выброшено InvalidClassException.
Для совпадающих версий работает мощная поддержка эволюции класса – совместимые изменения, такие как добавление или удаление полей, не приводят к InvalidClassException.
Неявное значение вычисляется автоматически в рантайме, и включает в себя информацию о имени типа, списке родителей и полей (с точностью до коллизии). По смыслу это похоже на хэш-сумму класса. Соответственно, при любом изменении класса значение изменится, и поддержка эволюции окажется бесполезной.
Всегда лучше явно указывать любое значение serialVersionUID, и изменять только в тех редких случаях, когда требуется сломать совместимость с предыдущими версиями. Стандартная утилита JDK serialver умеет «угадывать» авто-генерированное значение. Она используется чтобы зафиксировать значение для включения поддержки эволюции созданного ранее класса.
Явное значение устанавливается в переменную static final long serialVersionUID.
#Сериализация
⁉️Как работать с командой в Git?
🗓 9 июня в 20:00 на открытом уроке в OTUS разберем самые важные практические навыки командной работы Виталий Куценко, Java Lead в RND подразделении Ростсельмаша. На занятии поговорим про Pull Request, обсудим, как давать и получать обратную связь и почему это важно.
Ответим на вопросы, как
✔️ Делать доработки в рамках PR
✔️ Исправлять проблемы в PR
✔️ Решать конфликты и многое другое
📚Занятие пройдет в рамках углубленного онлайн-курса «Java Developer. Professional» для тех, кто уже установил и настроил свой Git.
📌Для участия пройдите вступительный тест:https://otus.pw/udJR/
Руководство по Java 8 Optional
В этом учебном пособии мы рассмотрим класс Optional, который был представлен в Java 8.
Цель класса — предоставить решение на уровне типа для представления опциональных значений вместо null (нулевых) ссылок.
Для более глубокого понимания того, почему мы должны обратить внимание на класс Optional, ознакомьтесь с официальной статьей Oracle.
Введение в Java Process Memory Model
Каждое Java приложение, после запуска, создаёт десятки, сотни, тысячи объектов в памяти компьютера на котором оно запущено. Память, при этом, ресурс не бесконечный, и поэтому необходимо использовать его эффективно. Виртуальная Машина Java (Java Virtual Machine, далее JVM) умеет граммотно распоряжаться памятью и помогает нам, разработчикам, управляя ею автоматически.
О том, как именно JVM работает с памятью во время работы Java приложения мы поговорим в этой статье.
👉 @BookJava
Зачем нужна Java Serialization? Как сделать класс сериализуемым?
Сериализация – это сохранение типа и состояния объекта в бинарном виде для последующего сохранения/передачи и десериализации. Для сериализации используется интерфейс Serializable (Externalizable), и цель записи/источник чтения ObjectInputStream/ObjectOutputStream (ObjectInput/ObjectOutput).
Класс сериализуем, если:
🔘 Реализует маркерный интерфейс Serializable;
🔘 Все поля сериализуемые или помечены модификаторомtransient (иначе рантайм выбросит NotSerializableException).
Протокол стандартной сериализации описан в документации.
Сериализационная форма может, и в некоторых случаях для корректной работы должна быть кастомизирована. Правильная форма содержит только логическое представление данных, без деталей о физической реализации.
Для описания полей сериализационной формы в javadoc-документации используется тэг @serial. Для документации генерирующего нестандартную сериализационную форму метода используется @serialData. Эти тэги имеют смысл и для приватных членов, так как эффективно такие члены – часть публичного API.
Нестатические внутренние классы не должны быть сериализуемыми. Статические поля как поля класса а не инстанса несериализуемы.
Сериализации посвящен целый раздел Effective Java. Доклад для ознакомления с темой.
#Сериализация
Модель памяти Java процесса
Рассуждаем о Java Memory Model и Garbage Collection'е.
Визуализируем память Java приложения.
Смотрим на красочный VisualGC.
Всё ради того, чтобы разобраться как работает JVM с памятью.
0:00 - Введение
0:39 - Тестовое приложение
1:34 - VisualVM
3:25 - Структура памяти
8:54 - Tenure Threshold
10:12 - Что ещё есть в VisualGC plugin?
12:24 - Завершение
👉 @BookJava
Из чего состоит String?
Ответ как обычно зависит от версии Java. Два поля, которые присутствовали во всех версиях – массив символов char[] value и int hash. В поле hash кэшируется хэш-сумма при первом подсчете для соблюдения контракта метода hashCode.
До Java 7 были еще поля offset и count – чтобы переиспользовать без пересоздания массивы из билдеров и других строк. В современной джаве от этого отказались в угоду меньшего потребления памяти.
Изначально все строки хранились в кодировке UTF-16, каждый символ занимал по два байта и умещался в char. Однако выяснилось, что статистически большинство строк содержит только ASCII-символы, которые вмещаются в один байт и составляют кодировку LATIN-1. То есть старший байт в большинстве char остается нулевым, и строки наполовину состоят из пустоты. А примерно четверть памяти приложений состоит из одних только строк.
В Java 6 была введена экспериментальная фича Compressed Strings – способность строки хранить строки в LATIN-1 в массиве byte вместо char. С этой фичей был ряд проблем, и позднее ее убрали.
Снова сжатие строк появилось в Java 9 – теперь оно называется Compact Strings и включено по умолчанию. В классе String появилось поле coder, которое переключает кодировки, и статический флаг COMPACT_STRINGS, выключающий фичу вообще. Тип массива value окончательно изменился с char[] на byte[].
Для полного обзора особенностей класса String стоит посмотреть доклады Алексея Шипилёва (1, 2).
#Строки
Умение создавать отказоустойчивые и масштабируемые архитектуры — востребованный крупными компаниями навык. Он пригодится в работе разработчикам, тимлидам и архитекторам. Одна из техник масштабирования баз данных — репликация. 🗓 8 июня в 20:00 пройдет открытый урок «Преимущества и недостатки различных видов репликации» в OTUS.
Что вас ждет на занятии?
- Разберем различные виды репликаций, обсудим смысл и назначение репликации
- Сравним особенности репликации в MySQL и PostgreSQL.
- Познакомимся с групповой репликацией в MySQL.
👉🏻 Пройдите вступительное тестирование, чтобы записаться на урок – https://otus.pw/1kGc/
Вебинар проведет эксперт по Java Enterprise разработке Владислав Родин. Продолжить общение со специалистами по высокой нагрузке вы сможете на онлайн-курсе «Highload Architect» от OTUS.
Пишем игру быки и коровы на Java
Существует множество вариаций этой игры. Компьютерный вариант игры обычно однопользовательский, при этом компьютер загадывает число, а человек — отгадывает его. После каждого ввода числа, компьютер выводит количество быков и коров в нем. «Коровой» называется цифра, угаданная без совпадения позиции, а «быком» — совпадение и цифры и позиции.
Помимо прочего, разработанная программа должна программа должна:
корректно обрабатывать неправильный пользовательский ввод (четырехзначные числа) и выдавать, при необходимости, предупреждающие сообщения;
сохранять таблицу рекордов в текстовом файле.
Задачи:
проанализировать задачу и разработать требования к программе;
выполнить анализ требований и проектирование;
реализовать программу и проверить правильность ее работы.
Исходный код работы целиком можно взять в репозитории.
👉 @BookJava
Как обойти строчку?
Для хранения строк в Java в общем случае используется кодировка UTF-16. Для полного понимания вопроса необходимо понимать ее особенности: что такое суррогатные пары и плоскости юникода. Конкретнее, что один символ в обычном понимании слова называется code point, и представляется одним или двумя значениями типа char. Значит, корректный ответ нужно начать с уточнения: подразумевается ли обход значений char или code point.
Из этого следует, что и длина строки, верхняя граница итерации – тоже понятие неоднозначное. Метод length() на самом деле возвращает не количество Unicode-символов, а количество значений char. Реальную логическую длину (количество кодовых точек) покажет метод codePointCount(). Нужно помнить, что чтобы обнаружить суррогатные пары, внутри ему придется проитерировать по символам.
Итерироваться по char можно либо получая по одному символу с помощью метода charAt(), либо со всем массивом сразу, методом toCharArray(). В случае с массивом создается копия внутреннего значения – это естественно медленнее, зато этот массив-копию можно мутировать. Работать с суррогатными парами придется вручную, для этого в классе Character есть специальные методы.
Другой вариант – сразу оперировать методами codePointAt() и codePointBefore(). Параметром указываются индексы массива char, но результатом будут кодовые точки типа int.
В Java 8 появился новый удобный способ обхода – методы chars() и codePoints(). Они возвращают IntStream из символов и кодовых точек соответственно. Носителем результирующих стримов выступает оригинальное внутреннее значение строки, копирование массива не требуется.
#Строки
🟢 Для новичков, обучение с нуля
🎯 Начать карьеру в этой области с нуля поможет специализация «Android Developer». Вас ждет 10 месяцев освоения трендов Android-разработки на Kotlin от экспертов-практиков из ведущих IT-компаний.
Вы шаг за шагом получите все необходимые для работы навыки: от синтаксиса Kotlin и принципов создания приложений до технологии и инструментов Middle+ уровня.
👉 Оставьте заявку и забронируйте место со скидкой
🔴 Для опытных Android-разработчиков
🦾 Как Android-разработчику перейти на новый уровень? Для этого нужно уметь проектировать архитектуру приложений, глубоко разбираться в Android SDK, выстраивать инфраструктуры с нуля, тестировать приложения и знать современные библиотеки и фреймворки.
Именно этим навыкам обучают на онлайн-курсе «Android Developer. Professional». На протяжении 5 месяцев вы будете работать над собственным проектом — тонким клиентом к сервису с публичным API, которое усилит ваше портфолио
👉 Пройдите вступительный тест и занимайте место на курсе по спец.цене
JPoint 2022 — Java-конференция от JUG Ru Group.
Она пройдет 13–15 июня, на 80% online, а 24 июня в Санкт-Петербурге будет offline-день.
Вас ждут 27 докладов от Java Champions и разработчиков из Huawei, МТС, Tinkoff, Одноклассников и других компаний. Поговорим об инструментах, внутренностях VM, базах данных, архитектуре, процессах, а также обсудим работу с Kotlin и Spring.
Среди докладов:
✔ «Becoming a More Effective Developer: Tips and Experiences»;
✔ «Thread Wars: проект Loom наносит ответный удар»;
✔ «Непрерывное профилирование в облаке с помощью eBPF»;
✔ «Индексы в PostgreSQL. Как понять, что создавать».
Подробности и полная программа — на сайте конференции.
При покупке билета на конференцию из категории «для частных лиц» используйте промокод: bookjava2022JRGpc
Как получить ip адрес компьютера на java?
Используйте InetAddress чтобы получить IP адрес компьютера на Java, ниже пример кода как пример:
import java.net.InetAddress;
import java.net.UnknownHostException;
public class Main {
public static void main(String args[]) {
try {
String ip = InetAddress.getLocalHost().getHostAddress();
// Вывод: 127.0.0.1
System.out.println(ip);
} catch (UnknownHostException e) {
e.printStackTrace();
}
}
}
#java
Подписывайтесь на канал 👉@coddy_academy
Какие бывают строковые классы?
Кроме очевидного класса String, в стандарте Java существует еще StringBuffer и StringBuilder. Класс String иммутабелен, а эти два вспомогательных класса реализуют для него паттерн Builder и служат способом редактирования строки без относительно дорогого пересоздания объекта.
Все методы StringBuffer синхронны. В Java 1.5 ему на замену пришел несинхронизированный вариант StringBuilder. Эта ситуация аналогична HashMap и Hashtable. В остальном эти два класса почти ничем не отличаются, имеют одинаковый набор методов и конструкторов.
Для буфера и билдера не работает синтаксический сахар строк:
🔘 Их нельзя создать литералом, вместо этого используется обычный конструктор;
🔘 Нельзя конкатенировать оператором +, вместо этого используются обычные методы insert и append.
Сам оператор конкатенации константных выражений, компилируется в интернированную строку, но для не-констант неявно использует StringBuilder.
#Строки
⁉️Хочешь открыть новые подходы к разработке на Java ?
🔥 Приходи на открытый урок OTUS «Как сбросить оковы NullPointerException»2 июня в 20:00. Мы посмотрим на Optional в Java, насколько он нам помогает творить, а также построим безумный пример, который поможет почувствовать силу данного шаблона.
🗣Занятие проведет Виталий Куценко, Java Lead в RND подразделении Ростсельмаша. После вебинара вас ждет еще больше инструментов бэкенд-разработки на онлайн-курсе «Java Developer. Professional».
📌Пройдите вступительный тест, чтобы зарегистрироваться на занятие: https://otus.pw/e8eu/