Java Geek
2.5K subscribers
256 photos
1 file
16 links
Практичные советы, лайфхаки и код для Java-разработчиков. Каждый пост — реальная польза. Учим Java на примерах.

По всем вопросам @evgenycarter
Download Telegram
Как влияет модификатор static на класс/метод/поле?

Для класса — позволяет создать static-класс, экземпляры которого создавать нельзя. Используется для создания утилитных классов.

Для метода — делает метод статическим, то есть он может быть вызван без создания экземпляра класса.

Для поля — создает поле, общее для всех экземпляров класса. Статическое поле существует в единственном экземпляре для класса.

Если кратко, static позволяет создавать классы/методы/поля, связанные с классом, а не с экземпляром.
Это удобно, когда нужно реализовать утилитные классы или объекты, общие для всех экземпляров.

👉 @java_geek
Что такое Atomic types и зачем они нужны?

Atomic типы — это классы, которые предоставляют методы для выполнения атомарных операций и используются в многопоточном программировании для обеспечения безопасности потоков без использования блоков synchronized.

Атомарные операции — это операции, которые выполняются как единое целое и не могут быть прерваны. Это означает, что если поток начинает выполнять атомарную операцию, никакой другой поток не может видеть промежуточное состояние или изменять состояние, пока операция не будет завершена.

Atomic типы, такие как AtomicInteger, AtomicLong, AtomicBoolean и т. д., предоставляют методы для выполнения атомарных операций, таких как get(), set(), getAndSet(), compareAndSet() и т. д.

Они полезны в многопоточном программировании, когда необходимо обеспечить целостность данных при одновременном доступе к общим данным из нескольких потоков. Использование Atomic типов может помочь избежать ошибок синхронизации и улучшить производительность по сравнению с использованием блоков synchronized, так как они не требуют блокировки.

👉 @java_geek
Метод delete() класса StringBuffer

Метод delete() в классе StringBuffer используется для удаления символов из строки. Он удаляет символы из строки, на которой он был вызван.

В качестве аргумента принимает начальный индекс и конечный индекс удаляемого фрагмента и сдвигает оставшиеся символы влево, замещая удаленные.
Возвращает ссылку на текущий объект StringBuffer.

👉 @java_geek
Метод trimToSize()

Метод trimToSize() используется для оптимизации размера внутреннего массива коллекций, таких как ArrayList или HashMap.
Этот метод позволяет уменьшить размер внутреннего массива коллекции до текущего количества элементов, то есть избавиться от неиспользуемой памяти.

Вызывать этот метод имеет смысл после массового удаления элементов из коллекции, чтобы освободить лишнюю память.
При добавлении новых элементов размер массива автоматически увеличится.

Метод trimToSize() является необязательной оптимизацией производительности и памяти. Его можно не вызывать, в этом случае внутренний массив будет занимать максимальный размер.

👉 @java_geek
StringBuffer

StringBuffer — это класс, предназначенный для работы со строками. Он позволяет создавать модифицируемые (изменяемые) строки.

В отличие от класса String, объекты StringBuffer можно изменять после их создания, используя различные методы, такие как append(), insert(), delete().
Также StringBuffer эффективнее String при частых изменениях строки, так как не создает новый объект при каждом изменении.

Класс является потокобезопасным, т. е. может использоваться в многопоточных приложениях.

Методы StringBuffer не синхронизированы, поэтому для многопоточного доступа нужно вручную синхронизировать доступ с помощью synchronized блока.

👉 @java_geek
Callable

Callable — это интерфейс из пакета java.util.concurrent, который представляет собой задачу, которую можно выполнить и получить результат, а также обработать исключение, если оно произошло во время выполнения задачи. Он аналогичен интерфейсу Runnable, но в отличие от Runnable, Callable может возвращать результат выполнения и бросать проверяемые исключения.

👉 @java_geek
Конвертируем массив в список

Arrays.asList() — это статический метод класса Arrays, который позволяет конвертировать обычный массив в список List.

— Принимает массив в качестве аргумента и возвращает объект типа List с элементами этого массива.

— Возвращаемый список имеет фиксированный размер, равный длине исходного массива. Добавлять/удалять элементы в него нельзя.

— Изменения в возвращаемом списке будут вноситься в исходный массив, т. к. список работает как «представление» массива. Метод работает для массивов примитивных и ссылочных типов.

Arrays.asList хорош для чтения элементов массива, но не для записи из-за неизменяемого размера.

👉 @java_geek
Как не допустить сериализацию?

Чтобы не допустить автоматическую сериализацию можно переопределить private методы для создания исключительной ситуации NotSerializableException.

private void writeObject(ObjectOutputStream out) throws IOException {
throw new NotSerializableException();
}

private void readObject(ObjectInputStream in) throws IOException {
throw new NotSerializableException();
}

👉 @java_geek
Как разделить строку на части?

В Java можно разделить строку на части с помощью метода split() класса String. Метод split() разбивает исходную строку на массив строк, используя заданный разделитель.

В этом примере исходная строка «Это пример строки для разделения» разбивается на части с помощью пробела в качестве разделителя. Однако, если у вас есть другой разделитель (например, запятая или точка с запятой), просто замените значение переменной delimiter на соответствующий разделитель в вашем случае.

👉 @java_geek
CyclicBarrier

CyclicBarrier (циклический барьер) — это один из механизмов синхронизации в языке программирования Java, предоставляемый пакетом java.util.concurrent. Он позволяет группе потоков синхронизироваться на определенной точке выполнения, после чего они могут продолжить выполнение параллельно.

CyclicBarrier представляет собой барьер, который блокирует выполнение всех потоков до тех пор, пока все потоки не достигнут этой точки. Как только все потоки достигли барьера, он разблокируется, и все потоки выполняют свою работу.

👉 @java_geek
Исключение в static блоке кода

Если в статическом блоке инициализации возникнет исключение, то это приведет к ошибке при инициализации класса.

Решить эту проблему можно двумя способами:

1. Перехватить исключение с помощью try-catch в этом же статическом блоке.
2. Перехватить исключение в последующем методе, куда оно будет выброшено, если не обрабатывать исключение в статическом блоке.

Как видно из примера, исключение из статического блока перехватывается в нем же блоком try-catch.
После этого класс инициализируется успешно, и его статический метод можно вызвать.

Если не обрабатывать исключение в статическом блоке, то оно будет выброшено дальше и его можно будет поймать в методе main, как показано в примере.

👉 @java_geek
Метод split

Метод split() используется для разбиения строки на подстроки по заданному разделителю. Он принимает один параметр — регулярное выражение, по которому будет производиться разбиение строки и возвращает массив строк (String[]), содержащий подстроки.

Если в качестве разделителя передать пробел (» «), то строка разбивается по пробелам на отдельные слова. Также можно указать число в качестве второго параметра, это будет лимит количества элементов.

👉 @java_geek
Какие основные принципы Stream API?

Stream API — это функциональный интерфейс в Java 8, который позволяет работать с коллекциями объектов с помощью функциональных операций.

Основные принципы Stream API включают в себя:

- Stream API не выполняет операции над элементами коллекции до тех пор, пока не будет вызван терминальный метод.

- Stream API представляет собой поток данных, который можно обрабатывать с помощью функциональных операций.

- Stream API предоставляет множество функциональных операций, таких как filter(), map(), reduce() и т. д., которые позволяют обрабатывать элементы потока данных.

- Stream API не изменяет исходную коллекцию, а создает новый поток данных на основе исходной коллекции.

- Stream API позволяет обрабатывать элементы потока данных параллельно, что может ускорить выполнение операций над большими коллекциями.

- Stream API требует вызова терминальной операции, такой как forEach(), collect() или reduce(), чтобы выполнить операции над элементами потока данных и получить результат.

👉 @java_geek
Что такое механизм try-with-resources?

Данная конструкция, которая появилась в Java 7, позволяет использовать блок try-catch не заботясь о закрытии ресурсов, используемых в данном сегменте кода. Ресурсы объявляются в скобках сразу после try, а компилятор уже сам неявно создаёт секцию finally, в которой и происходит освобождение занятых в блоке ресурсов. Под ресурсами подразумеваются сущности, реализующие интерфейс java.lang.Autocloseable.

Стоит заметить, что блоки catch и явный finally выполняются уже после того, как закрываются ресурсы в неявном finally.

👉 @java_geek
Метод weakCompareAndSwap()

Метод weakCompareAndSwap() используется для атомарного обновления полей объекта без блокировки.

Он позволяет сравнить значение поля с ожидаемым значением и установить новое значение, если они равны. Это полезно при реализации неблокирующих алгоритмов параллельного программирования.

В этом примере два потока пытаются атомарно изменить значение счетчика с 0 на 1 и 2 соответственно. Метод weakCompareAndSwap гарантирует, что только один поток сможет успешно выполнить изменение.

👉 @java_geek
Класс DateTimeFormatter

Класс DateTimeFormatter используется для форматирования и парсинга объектов даты и времени.

Он позволяет указать нужный формат даты и времени при выводе этих данных в строку или при чтении из строки в объекты LocalDateTime, LocalDate и другие классы API даты и времени.

👉 @java_geek
Метод executeQuery()

Метод executeQuery() в Java используется для выполнения запросов на выбор данных из базы данных. Он возвращает объект ResultSet, который представляет набор данных, возвращаемый запросом.

Синтаксис метода executeQuery() следующий:

public ResultSet executeQuery(String sql) throws SQLException;

Аргумент sql представляет собой строку, содержащую SQL-запрос. Возвращаемое значение метода executeQuery() — это объект ResultSet, который представляет собой набор данных, возвращаемый запросом. Объект ResultSet содержит информацию о столбцах данных, содержащихся в наборе данных, а также данные из каждого столбца.

👉 @java_geek
В чем отличия между TreeSet и HashSet?

Основное отличие между TreeSet и HashSet заключается в том, что TreeSet хранит элементы в отсортированном порядке, в то время как порядок хранения элементов в HashSet не определен. TreeSet также обеспечивает быстрый поиск и извлечение элементов в отсортированном порядке.

👉 @java_geek
Apache Commons CLI

Apache Commons CLI (Commons Command Line Interface) — это библиотека для обработки аргументов командной строки в Java. Она предоставляет удобный способ определения и обработки аргументов командной строки для ваших Java-приложений. Библиотека Apache Commons CLI упрощает работу с аргументами командной строки, включая разбор аргументов, создание справки и обработку различных опций командной строки.

👉 @java_geek
Реверс массива

Реверс массива в Java означает изменение порядка элементов массива на противоположный. То есть, элементы, которые изначально были в начале массива, становятся в конце, и наоборот.

Реверс массива может быть полезным во многих ситуациях программирования. Например, это может потребоваться для изменения порядка элементов перед их обработкой или выводом, или для выполнения действий, которые требуют доступа к элементам массива в обратном порядке.

👉 @java_geek
Какие классы поддерживают чтение и запись потоков в компрессированном формате?

В Java для работы с потоками в сжатом формате используются классы из пакета java.util.zip:

ZipInputStream и ZipOutputStream — для чтения и записи архивов в формате ZIP.
GZIPInputStream и GZIPOutputStream — для чтения и записи файлов в формате GZIP.
InflaterInputStream и DeflaterOutputStream — для чтения и записи данных в формате ZLIB.

Эти классы являются обертками потоков ввода/вывода и позволяют прозрачно читать и записывать сжатые данные, как если бы речь шла о обычных потоках.

👉 @java_geek