Есть несколько видов ссылок на методы:
1️⃣ Ссылка на статический метод
Используется для вызова статических методов класса.
Синтаксис:
ContainingClass::staticMethodName
Пример:
import java.util.function.Function;
public class MethodReferenceExample {
public static void main(String[] args) {
Function<String, Integer> converter = Integer::parseInt;
Integer number = converter.apply("123");
System.out.println(number); // 123
}
}
2️⃣ Ссылка на метод экземпляра конкретного объекта
Используется для вызова методов экземпляра объекта.
Синтаксис:
containingObject::instanceMethodName
Пример:
import java.util.Arrays;
import java.util.List;
public class MethodReferenceExample {
public static void main(String[] args) {
List<String> names = Arrays.asList("Alice", "Bob", "Charlie");
names.forEach(System.out::println);
}
}
3️⃣ Ссылка на метод экземпляра произвольного объекта определенного типа
Синтаксис:
ContainingType::methodName
Пример:
import java.util.function.Function;
public class FunctionExample {
public static void main(String[] args) {
Function<String, Integer> stringLength = String::length;
Integer length = stringLength.apply("Hello, World!");
System.out.println(length); // 13
}
}
Отличие от предыдущего вида в том, что в предыдущем ссылка на метод получается у конкретного объекта, стало быть вызовется метод этого объекта, а в нашем случае при получении ссылки на метод, мы знаем только метод, но объект у которого вызовется этот метод еще не известен, он будет предоставлен при вызове метода. Код выше будет означать "Hello, World!".length()
4️⃣ Ссылка на конструктор
Используется для вызова конструктора.
Синтаксис:
ClassName::new
Пример:
import java.util.function.Supplier;
public class MethodReferenceExample {
public static void main(String[] args) {
Supplier<MethodReferenceExample> exampleSupplier = MethodReferenceExample::new;
MethodReferenceExample example = exampleSupplier.get();
System.out.println(example); // MethodReferenceExample@<hashcode>
}
}
#java #MethodReference
Please open Telegram to view this post
VIEW IN TELEGRAM
👍9❤4
Цикл for со счетчиком
for (initialization; condition; update) {
// тело цикла
}
Описание:
initialization: выполняется один раз перед началом цикла. Обычно используется для инициализации счетчика.
condition: проверяется перед каждой итерацией. Если условие истинно, выполняется тело цикла.
update: выполняется после каждой итерации. Обычно используется для изменения счетчика.
int[] numbers = {1, 2, 3, 4, 5};
for (int i = 0; i < numbers.length; i++) {
System.out.println(i + ": " + numbers[i]);
}
Применение:
Используется, когда известно количество итераций заранее. Часто применяется для работы с массивами или коллекциями, когда нужен индекс.
Цикл for-each
for (type element : collection) {
// тело цикла
}
Описание:
Итерируется по каждому элементу коллекции (например, массива, списка, множества). Обеспечивает удобный способ доступа к каждому элементу без использования индексов.
int[] numbers = {1, 2, 3, 4, 5};
for (int number : numbers) {
System.out.println(number);
}
Применение:
Предпочтителен, когда не нужен доступ к индексам элементов.
Цикл while
while (condition) {
// тело цикла
}
Описание:
condition: проверяется перед каждой итерацией. Если условие истинно, выполняется тело цикла.
String code = UUID.randomUUID().toString();
boolean isCodeExists = repo.isCodeExists(code);
while (isCodeExists) {
code = UUID.randomUUID().toString();
isCodeExists = repo.isCodeExists(code);
}
repo.saveCode(code);
Применение:
Используется, когда количество итераций неизвестно заранее и определяется во время выполнения программы. Цикл может не выполниться ни одного раза.
Цикл do-while
do {
// тело цикла
} while (condition);
Описание:
Выполняет тело цикла хотя бы один раз, а затем проверяет условие condition. Если условие истинно, цикл повторяется.
String command;
do {
command = readCommand();
doCommand(command);
} while (!"EXIT".equals(command));
Применение:
Используется, когда тело цикла должно выполниться хотя бы один раз, независимо от условия. Часто применяется для меню или ввода данных, где сначала нужно выполнить действие, а затем проверить условие.
#java #cycles #for #while
Please open Telegram to view this post
VIEW IN TELEGRAM
👍8❤1
Heap (куча) используется Java Runtime для выделения памяти под объекты и классы. Создание нового объекта также происходит в куче. Это же является областью работы сборщика мусора. Любой объект, созданный в куче, имеет глобальный доступ и на него могут ссылаться из любой части приложения.
Stack (стек) это область хранения данных также находящееся в общей оперативной памяти (RAM). Всякий раз, когда вызывается метод, в памяти стека создается новый блок, который содержит примитивы и ссылки на другие объекты в методе. Как только метод заканчивает работу, блок также перестает использоваться, тем самым предоставляя доступ для следующего метода. Размер стековой памяти намного меньше объема памяти в куче. Стек в Java работает по схеме LIFO (Последний-зашел-Первый-вышел)
Различия между Heap и Stack памятью:
✔️ Куча используется всеми частями приложения, в то время как стек используется только одним потоком исполнения программы.
✔️ Всякий раз, когда создается объект, он всегда хранится в куче, а в памяти стека содержится лишь ссылка на него. Память стека содержит только локальные переменные примитивных типов и ссылки на объекты в куче.
✔️ Объекты в куче доступны с любой точки программы, в то время как стековая память не может быть доступна для других потоков.
✔️ Стековая память существует лишь какое-то время работы программы, а память в куче живет с самого начала до конца работы программы.
✔️ Если память стека полностью занята, то Java Runtime бросает исключение java.lang.StackOverflowError. Если заполнена память кучи, то бросается исключение java.lang.OutOfMemoryError: Java Heap Space.
✔️ Размер памяти стека намного меньше памяти в куче.
✔️ Из-за простоты распределения памяти, стековая память работает намного быстрее кучи.
Для определения начального и максимального размера памяти в куче используются -Xms и -Xmx опции JVM. Для стека определить размер памяти можно с помощью опции -Xss.
#java #heap #stack #memory
Please open Telegram to view this post
VIEW IN TELEGRAM
👍9❤2🔥1
В Java 12 появился новый синтаксис для
switch, который позволяет возвращать значение используя стрелки ->, что делает код более компактным и удобным. Теперь switch может использоваться как выражение, а не только как оператор, что упрощает его применение в логике.Ранее
switch использовался как оператор, и код мог выглядеть громоздко:
String day = "MONDAY";
int numLetters;
switch (day) {
case "MONDAY":
case "FRIDAY":
case "SUNDAY":
numLetters = 6;
break;
case "TUESDAY":
numLetters = 7;
break;
default:
numLetters = 8;
}
System.out.println(numLetters); // Вывод: 6
Со Switch Expressions можно переписать этот код более лаконично:
String day = "MONDAY";
int numLetters = switch (day) {
case "MONDAY", "FRIDAY", "SUNDAY" -> 6;
case "TUESDAY" -> 7;
default -> 8;
};
System.out.println(numLetters); // Вывод: 6
Теперь
switch может вернуть значение, и нет необходимости в break.#java #switch
Please open Telegram to view this post
VIEW IN TELEGRAM
👍22❤3
Общий совет: выбирать поля, которые с большой долью вероятности будут различаться. Для этого необходимо использовать уникальные, лучше всего примитивные поля, например, такие как id, uuid. При этом нужно следовать правилу, если поля задействованы при вычислении
hashCode(), то они должны быть задействованы и при выполнении equals().#java #hashCode #equals
Please open Telegram to view this post
VIEW IN TELEGRAM
👨💻6❤2
В Java лямбда-выражения используются с функциональными интерфейсами, которые имеют ровно один абстрактный метод. Например, стандартный функциональный интерфейс
Function из пакета java.util.function представляет собой типичный пример.Для нашего примера используем встроенный функциональный интерфейс
IntUnaryOperator. Он выглядит вот так:
@FunctionalInterface
public interface IntUnaryOperator {
int applyAsInt(int operand);
}
Этот интерфейс представляет функцию, которая принимает один аргумент типа
int и возвращает значение типа int.
import java.util.function.IntUnaryOperator;
public class Main {
public static int applyOperation(int number, IntUnaryOperator operator) {
return operator.applyAsInt(number);
}
public static void main(String[] args) {
int number = 5;
// Лямбда-выражение для удвоения значения
IntUnaryOperator doubleOperation = x -> x * 2;
System.out.println("Double: " + applyOperation(number, doubleOperation)); // Double: 10
// Лямбда-выражение для увеличения значения на 10
IntUnaryOperator addTenOperation = x -> x + 10;
System.out.println("Add Ten: " + applyOperation(number, addTenOperation)); // Add Ten: 15
}
}
В нашем примере метод
applyOperation принимает два параметра: число и функциональный интерфейс IntUnaryOperator. Лямбда-выражение используется для определения конкретной функции.#java #lambda #IntUnaryOperator
Please open Telegram to view this post
VIEW IN TELEGRAM
👍6❤2
Object это базовый класс для всех остальных объектов в Java. Любой класс наследуется от Object и, соответственно, наследуют его методы:public boolean equals(Object obj) – служит для сравнения объектов по значению;int hashCode() – возвращает hash код для объекта;String toString() – возвращает строковое представление объекта;Class getClass() – возвращает класс объекта во время выполнения;protected Object clone() – создает и возвращает копию объекта;void notify() – возобновляет поток, ожидающий монитор;void notifyAll() – возобновляет все потоки, ожидающие монитор;void wait() – остановка вызвавшего метод потока до момента пока другой поток не вызовет метод notify() или notifyAll() для этого объекта;void wait(long timeout) – остановка вызвавшего метод потока на определённое время или пока другой поток не вызовет метод notify() или notifyAll() для этого объекта;void wait(long timeout, int nanos) – остановка вызвавшего метод потока на определённое время или пока другой поток не вызовет метод notify() или notifyAll() для этого объекта;protected void finalize() – может вызываться сборщиком мусора в момент удаления объекта при сборке мусора.#java #Object #methods
Please open Telegram to view this post
VIEW IN TELEGRAM
👍8❤3
Дан список людей с именем и городом проживания. Нужно сгруппировать их по городам.
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;
record Person(String name, String city) {}
public class StreamExample {
public static void main(String[] args) {
List<Person> people = List.of(
new Person("Alice", "New York"),
new Person("Bob", "Los Angeles"),
new Person("Charlie", "New York"),
new Person("David", "Los Angeles"),
new Person("Edward", "San Francisco")
);
Map<String, List<Person>> peopleByCity = people.stream()
.collect(Collectors.groupingBy(Person::city));
peopleByCity.forEach((city, peopleInCity) -> {
System.out.println(city + ": " + peopleInCity.stream()
.map(Person::name)
.collect(Collectors.joining(", ")));
});
// Вывод:
// San Francisco: Edward
// New York: Alice, Charlie
// Los Angeles: Bob, David
}
}
#java #stream #grouping
Please open Telegram to view this post
VIEW IN TELEGRAM
1👍14🔥4❤3
В микросервисной архитектуре наблюдаемость — не роскошь, а умение выжить в проде. Как сделать качественный мониторинг без затратных решений? Ответ в новой статье от Anderson Kuntz Meurer.
@RestController к метрикам — HTTP‑статы, latency, ошибки.Please open Telegram to view this post
VIEW IN TELEGRAM
❤2
Maven использует жизненный цикл сборки, который делится на несколько фаз. Фазы определяют последовательность задач, которые Maven выполняет для сборки и управления проектом.
Основные фазы жизненного цикла Maven включают:
1️⃣ validate – Проверяет, что проект правильный и вся необходимая информация указана.
2️⃣ compile – Компилирует исходный код проекта.
3️⃣ test – Запускает тесты (обычно с использованием JUnit или TestNG) и проверяет, что они проходят успешно.
4️⃣ package – Собирает скомпилированный код и пакует его, например, в JAR или WAR-файл.
5️⃣ verify – Проверяет собранные артефакты и результаты тестов.
6️⃣ install – Устанавливает пакет в локальный репозиторий для использования как зависимость в других проектах.
7️⃣ deploy – Отправляет финальный пакет в удаленный репозиторий для использования в других проектах или на сервере.
Основные команды Maven:
✔️
mvn clean – Удаляет папку target, очищая проект от предыдущих сборок.✔️
mvn compile – Компилирует исходный код проекта.✔️
mvn test – Запускает тесты.✔️
mvn package – Пакует скомпилированный код в конечный артефакт (обычно JAR или WAR).✔️
mvn install – Устанавливает артефакт в локальный репозиторий.✔️
mvn deploy – Деплоит артефакт в удаленный репозиторий.✔️
mvn site – Генерирует документацию проекта на основе кода и зависимостей.Фазы выполняются последовательно, то есть если вы запускаете команду
mvn install, Maven автоматически пройдет через все предыдущие фазы – от validate до install.Примеры команд:
✔️
mvn clean install – очищает проект, компилирует, тестирует и устанавливает артефакт в локальный репозиторий.✔️
mvn package -DskipTests – собирает проект в артефакт, пропуская тесты.#java #Maven
Please open Telegram to view this post
VIEW IN TELEGRAM
👍18❤3🔥3
Дженерики позволяют определить параметр типа, который будет заменен конкретным типом данных при создании экземпляра класса или вызове метода. Например,
List<T> может использоваться как List<String>, List<Integer> и т.д.Благодаря дженерикам, ошибки типа (например, попытка вставить объект неправильного типа) обнаруживаются на этапе компиляции, а не во время выполнения программы.
Один универсальный класс или метод может работать с различными типами данных, что позволяет избежать дублирования кода.
Во время компиляции информация о типах стирается, и вместо этого используется базовый тип, что позволяет сохранять совместимость с кодом, написанным до появления дженериков.
public class Box<T> {
private T item;
public void setItem(T item) {
this.item = item;
}
public T getItem() {
return item;
}
}
Box<String> stringBox = new Box<>();
stringBox.setItem("Hello");
String str = stringBox.getItem();
В этом примере класс
Box<T> является обобщенным и может работать с любым типом данных, который заменит T при создании объекта.#java #generics #T
Please open Telegram to view this post
VIEW IN TELEGRAM
👍16❤5🔥4
java.util. Он облегчает создание текстовых последовательностей, объединяя строки и вставляя разделители между ними.Вызов метода
toString() возвращает объединенную строку с разделителями и окружающими символами.Вы также можете использовать метод
setEmptyValue() для определения значения, которое будет использоваться, если StringJoiner остается пустым.
StringJoiner sj = new StringJoiner(", ", "[" , "]");
sj.setEmptyValue("No items");
System.out.println(sj.toString()); // No items
sj.add("Apple").add("Banana").add("Cherry");
System.out.println(sj.toString()); // [Apple, Banana, Cherry]
#java #StringJoiner
Please open Telegram to view this post
VIEW IN TELEGRAM
❤12👍9🔥4
Java является строго типизированным языком программирования, а это означает, то что каждое выражение и каждая переменная имеет строго определенный тип уже на момент компиляции. Однако определен механизм приведения типов (casting) - способ преобразования значения переменной одного типа в значение другого типа.
В Java существуют несколько разновидностей приведения:
✔️ Тождественное (identity). Преобразование выражения любого типа к точно такому же типу всегда допустимо и происходит автоматически.
✔️ Расширение (повышение, upcasting) примитивного типа (widening primitive). Означает, что осуществляется переход от менее емкого типа к более ёмкому. Например, от типа
byte (длина 1 байт) к типу int (длина 4 байта). Такие преобразование безопасны в том смысле, что новый тип всегда гарантировано вмещает в себя все данные, которые хранились в старом типе и таким образом не происходит потери данных. Этот тип приведения всегда допустим и происходит автоматически.✔️ Сужение (понижение, downcasting) примитивного типа (narrowing primitive). Означает, что переход осуществляется от более емкого типа к менее емкому. При таком преобразовании есть риск потерять данные. Например, если число типа
int было больше 127, то при приведении его к byte значения битов старше восьмого будут потеряны. В Java такое преобразование должно совершаться явным образом, при этом все старшие биты, не умещающиеся в новом типе, просто отбрасываются - никакого округления или других действий для получения более корректного результата не производится.✔️ Расширение объектного типа (widening reference). Означает неявное восходящее приведение типов или переход от более конкретного типа к менее конкретному, т.е. переход от потомка к предку. Разрешено всегда и происходит автоматически.
✔️ Сужение объектного типа (narrowing reference). Означает нисходящее приведение, то есть приведение от предка к потомку (подтипу). Возможно только если исходная переменная является подтипом приводимого типа. При несоответствии типов в момент выполнения выбрасывается исключение
ClassCastException. Требует явного указания типа.✔️ Преобразование к строке (to String). Любой тип может быть приведен к строке, т.е. к экземпляру класса
String.✔️ Запрещенные преобразования (forbidden). Не все приведения между произвольными типами допустимы. Например, к запрещенным преобразованиям относятся приведения от любого ссылочного типа к примитивному и наоборот (кроме преобразования к строке). Кроме того, невозможно привести друг к другу классы, находящиеся на разных ветвях дерева наследования и т.п.
При приведении ссылочных типов с самим объектом ничего не происходит, - меняется лишь тип ссылки, через которую происходит обращение к объекту.
Для проверки возможности приведения нужно воспользоваться оператором
instanceof:
Parent parent = new Child();
if (parent instanceof Child) {
Child child = (Child) parent;
}
#java #casting #upcasting #downcasting
Please open Telegram to view this post
VIEW IN TELEGRAM
👍10❤3🔥2
Integer a = 128;
Integer b = 128;
System.out.println(a == b); // false
Integer x = 1;
Integer y = 1;
System.out.println(x == y); // true
Это не просто волшебство! Это связано с целочисленным кэшированием в Java.
Для значений в диапазоне от -128 до 127 объекты типа
Integer кэшируются, и ссылки на них одинаковы, а для значений за пределами этого диапазона создаются новые объекты, и ссылки на них будут разными. Так как используется оператор ==, то сравниваются ссылки на объекты.#java #magic
Please open Telegram to view this post
VIEW IN TELEGRAM
👍18❤2
Text Blocks (
""") позволяют удобно работать с многострочными строками без необходимости экранировать кавычки.• Улучшают читаемость кода.• Поддерживают форматирование и перенос строк.• Упрощают работу с JSON, SQL и HTML.
String json = """
{
"name": "Alice",
"age": 30
}
""";
System.out.println(json);
#java #textblocks #java15
Please open Telegram to view this post
VIEW IN TELEGRAM
👍10❤3🔥3
1. Обычные классы (Regular Classes)
Это наиболее распространенные классы, которые вы создаете для определения объектов. Они могут содержать поля, методы, конструкторы и вложенные классы.
public class MyClass {
private int field;
public MyClass(int field) {
this.field = field;
}
public void method() {
// some code
}
}
2. Абстрактные классы (Abstract Classes)
Абстрактные классы не могут быть созданы как объекты напрямую. Они предназначены для предоставления общей функциональности, которую подклассы должны реализовать или дополнить.
public abstract class AbstractClass {
public abstract void abstractMethod();
public void concreteMethod() {
// some code
}
}
3. Вложенные классы (Nested Classes)
Классы, объявленные внутри другого класса. Они могут быть статическими или нестатическими.
🔹 Статические вложенные классы (Static Nested Classes):
Эти классы могут быть созданы без экземпляра внешнего класса.
public class OuterClass {
static class StaticNestedClass {
// some code
}
}
🔹 Внутренние классы (Inner Classes):
Эти классы имеют доступ ко всем членам внешнего класса и создаются в контексте экземпляра внешнего класса.
public class OuterClass {
class InnerClass {
// some code
}
}
4. Локальные классы (Local Classes)
Классы, объявленные внутри метода, конструктора или блока. Они имеют доступ к финальным переменным из охватывающего метода.
public class OuterClass {
public void method() {
class LocalClass {
// some code
}
LocalClass local = new LocalClass();
}
}
5. Анонимные классы (Anonymous Classes)
Классы без имени, создаваемые на месте для реализации интерфейса или наследования от класса. Часто используются для создания экземпляров интерфейсов или абстрактных классов.
public class OuterClass {
public void method() {
Runnable runnable = new Runnable() {
@Override
public void run() {
// some code
}
};
}
}
6. Перечисления (Enums)
Специальные классы, представляющие набор констант. Они могут содержать поля, методы и конструкторы.
public enum Day {
MONDAY, TUESDAY, WEDNESDAY, THURSDAY, FRIDAY, SATURDAY, SUNDAY
}
7. Интерфейсы (Interfaces)
Технически не классы, но важная часть объектно-ориентированного программирования в Java. Интерфейсы определяют контракты, которые должны быть реализованы классами.
public interface MyInterface {
void myMethod();
}
8. Записи (Records)
Нововведение в Java 14 (в предварительном виде) и официально в Java 16. Они предоставляют компактный способ создания неизменяемых классов с полями и автоматически сгенерированными методами, такими как
equals, hashCode и toString.
public record Point(int x, int y) {}
#java #classes
Please open Telegram to view this post
VIEW IN TELEGRAM
👍16❤7🔥3
ArrayList — это реализация динамического массива из стандартной библиотеки коллекций java.util. Он представляет собой список, который может изменять свой размер в зависимости от количества добавляемых элементов. ArrayList основан на массиве объектов. Это означает, что под капотом у него есть массив фиксированного размера. Когда этот массив заполняется, создается новый массив большего размера, в который копируются элементы старого массива, а затем старый массив удаляется.Размер и емкость
✔️ Размер (size) — это количество элементов, которые фактически содержатся в
ArrayList.✔️ Емкость (capacity) — это текущий размер внутреннего массива. Когда количество элементов превышает емкость, массив расширяется.
Когда
ArrayList инициализируется, его емкость по умолчанию равна 10. Если количество элементов в массиве превышает емкость, массив автоматически увеличивается. Обычно емкость увеличивается по формуле: новая емкость = старая емкость * 1.5.Для удаления элементов используется метод
remove(int index). После удаления элемента все элементы, находящиеся справа от удаленного, смещаются на одну позицию влево, что требует временных затрат O(n).После удаления элементов
ArrayList не автоматически уменьшает емкость внутреннего массива, то есть массив может занимать больше памяти, чем требуется для хранения фактических элементов. Однако для оптимизации можно вручную уменьшить емкость до текущего размера с помощью метода trimToSize().Одним из преимуществ
ArrayList является возможность доступа к элементам по индексу за время O(1). Это возможно благодаря тому, что элементы хранятся в массиве, и доступ к ним осуществляется через индекс.#java #ArrayList
Please open Telegram to view this post
VIEW IN TELEGRAM
👍15❤3🥰1
В Java с версии 9 появилась возможность использовать
private методы в интерфейсах. Эти методы предназначены для улучшения внутренней организации интерфейсов, позволяя избежать дублирования кода в default и static методах. private методы помогают реализовать общую логику, к которой могут обращаться другие методы интерфейса, но они остаются недоступными для классов, реализующих интерфейс.private методы могут быть как экземплярными, так и static.Пример:
public interface MyInterface {
default void showMessage() {
print("Default method calling private method");
}
static void showStaticMessage() {
print("Static method calling private method");
}
// Private method for reuse
private static void print(String message) {
System.out.println(message);
}
}
#java #interface #private
Please open Telegram to view this post
VIEW IN TELEGRAM
❤6👍4🔥1
В отличие от Queue, элементы PriorityQueue не упорядочены по времени их добавления, а по приоритету.
Основные методы:
add(E e) - добавляет элемент в очередь.
remove() - удаляет и возвращает элемент с наивысшим приоритетом. Если очередь пуста, генерируется исключение
NoSuchElementException.poll() - удаляет и возвращает элемент с наивысшим приоритетом. Если очередь пуста, возвращает
null.peek() - возвращает, но не удаляет элемент с наивысшим приоритетом. Если очередь пуста, возвращает null.
element() - возвращает, но не удаляет элемент с наивысшим приоритетом. Если очередь пуста, генерируется исключение
NoSuchElementException.Пример:
class Task implements Comparable<Task> {
String name;
Integer priority;
public Task(String name, Integer priority) {
this.name = name;
this.priority = priority;
}
@Override
public int compareTo(@NotNull Task o) {
return priority - o.priority;
}
}
public class Test {
public static void main(String[] args) {
PriorityQueue<Task> pq = new PriorityQueue<>();
pq.add(new Task("Task1", 1));
pq.add(new Task("Task5", 5));
pq.add(new Task("Task2", 2));
pq.add(new Task("Task4", 4));
pq.add(new Task("Task3", 3));
while (!pq.isEmpty()) {
System.out.println(pq.poll().name);
// Выведет: Task1, Task2, Task3, Task4, Task5
}
}
}
#java #PriorityQueue
Please open Telegram to view this post
VIEW IN TELEGRAM
👍7❤4
В Java коллекции Map предоставляют возможность хранить пары "ключ-значение". Два популярных варианта —
HashMap и TreeMap. Давайте разберем их ключевые особенности и когда их лучше использовать.📚 Kраткие определения:
-
HashMap: - Неупорядоченная коллекция.
- Основан на хэш-таблице.
-
TreeMap: - Упорядоченная коллекция.
- Основан на красно-черном дереве.
- Поддерживает сортировку по ключам.
⚖️ Когда использовать:
-
HashMap:- Если важна производительность и порядок хранения не имеет значения.
- Когда нужно быстро получать значения по ключу
-
TreeMap:- Если необходимо хранить элементы в отсортированном порядке.
- Для использования функционала "примитивного" поиска (например,
firstKey() или lastKey()).📌 Подведение итогов:
Выбор между
HashMap и TreeMap зависит от ваших требований к производительности и порядку элементов. Помните, что HashMap лучше подходит для большинства случаев, когда необходим быстрый доступ, а TreeMap — для упорядоченного хранения данных.#java #HashMap #TreeMap
Please open Telegram to view this post
VIEW IN TELEGRAM
👍9❤1