10986
📚 Лайфхаки, приёмы и лучшие практики для Java-разработчиков. Всё, что ускорит код и прокачает навыки. Java, Spring, Maven, Hibernate. По всем вопросам @evgenycarter РКН clck.ru/3KoGeP
💻Хотите быстро научиться строить интерактивные интерфейсы на C#?
Присоединяйтесь к открытому уроку 8 апреля в 20:00 мск, где мы покажем, как сделать ваш код живым и динамичным!
📖Вы научитесь использовать класс System.Console для создания простых, но интересных программ с текстовыми интерфейсами. Например, вы напишете свою версию игры "Крестики-нолики" прямо в консоли. Это легко и увлекательно!
🔥С этим знанием вы сможете не просто выводить данные, а создавать интерактивные приложения, которые смогут реагировать на действия пользователя.
➡️ Зарегистрируйтесь на вебинар и получите скидку по промокоду SHARP_SPEC_4 на большое обучение «C# Developer»: https://vk.cc/cKzfGN
Промокод действителен до 30.04.2025
Реклама. ООО «Отус онлайн-образование», ОГРН 1177746618576
👨💻 Как уменьшить количество boilerplate-кода с помощью Lombok
Сегодня хочу показать вам один из любимых инструментов — Project Lombok. Он позволяет избавиться от тонны шаблонного кода, который мы ежедневно пишем в Java.
🔹 Вместо десятков строк с геттерами, сеттерами, equals/hashCode и конструкторами, ты просто добавляешь аннотации:
@Data
@AllArgsConstructor
@NoArgsConstructor
public class User {
private String name;
private int age;
}
toString(), equals() и hashCode()@Builder? Он тоже есть! И позволяет удобно создавать объекты:
User user = User.builder()
.name("Женя")
.age(30)
.build();
👩💻 Сообщения, которые не теряются: Брокеры против хаоса в Java
Приглашаем на открытый урок.
🗓 08 апреля в 20:00 МСК
🆓 Бесплатно. Урок в рамках старта курса «Java Developer. Professional».
Узнайте, как обеспечить 100% доставку данных в распределенных Java-системах: боремся с потерями, хаосом и scaling-вызовами.
О чём поговорим:
✔️Брокеры vs хаос: Как Kafka, RabbitMQ и ActiveMQ спасают данные от потерь.
✔️ Асинхронный Java на практике: Пишем код с гарантированной доставкой сообщений.
✔️ Антипаттерны: Топ-5 ошибок, которые приводят к краху системы (и как их избежать).
Кому будет интересно:
Вебинар будет полезен разработчикам, архитекторам и специалистам по интеграции, работающим с распределенными системами и стремящимся обеспечить надежную доставку данных.
В результате урока:
Участники научатся выбирать брокеры под задачи, реализовывать паттерны вроде Publisher-Subscriber , а также получат шаблоны кода для интеграции в свои проекты.
🔗 Ссылка на регистрацию: https://vk.cc/cKqBkW
Реклама. ООО «Отус онлайн-образование», ОГРН 1177746618576
💡Совет: @TransactionalEventListener — это специализированная версия @EventListener, которая прослушивает событие и ждёт завершения текущей транзакции, прежде чем сработать.
Ожидание согласованного состояния базы данных позволяет безопаснее реагировать на изменения, внесённые в БД ✨
#Java #springboot
👉@BookJava
💡 Collection vs List в Java: в чём разница и когда что использовать
Сегодня разберёмся с одним из самых популярных вопросов у джавистов: чем отличается Collection от List и когда что применять.
🔹 Collection — это базовый интерфейс всех коллекций в Java. Он описывает общие операции: add(), remove(), size(), contains() и т.д.
🔹 List — это подинтерфейс Collection, предназначенный для работы с упорядоченными списками.
Дополнительно даёт методы: get(index), set(index, value), indexOf(), add(index, value).
🔧 Пример с Collection:
Collection<String> names = new ArrayList<>();
names.add("Alice");
names.add("Bob");
for (String name : names) {
System.out.println(name);
}
List<String> cities = new ArrayList<>();
cities.add("Moscow");
cities.add("Berlin");
cities.add(1, "Paris");
System.out.println(cities.get(1)); // Paris
List.Collection, если хочешь абстрагироваться от конкретной структуры и не используешь индексы.List, если:Collection — так ты не ограничиваешь пользователя в реализации. List.
🧵 Как правильно логировать ошибки в Java-приложении
Привет, друзья! Сегодня я расскажу о простой, но критически важной теме — логирование ошибок. Часто вижу, как разработчики либо совсем не логируют исключения, либо делают это неправильно. В итоге: баг есть, а откуда он взялся — непонятно.
Вот пара реальных примеров:
❌ Плохо:
try {
doSomething();
} catch (Exception e) {
System.out.println("Error happened");
}
private static final Logger logger = LoggerFactory.getLogger(MyClass.class);
try {
doSomething();
} catch (Exception e) {
logger.error("Failed to do something", e);
}
logger.error позволяет видеть стек исключения, а это ключ к диагностике.logger.warn или logger.info в зависимости от уровня важности.traceId, userId, requestId и другие полезные метаданные.
Docker и Spring Boot микросервис (Быстрый старт)
Разберем основные понятия докера и запустим spring boot микросервис в докере
00:00 Intro
00:58 Установить докер
02:05 Развитие виртуализации
09:30 Компоненты Docker
11:25 Docker Daemon
11:50 Dockerfile
12:42 Docker Image
13:12 Docker Registry
13:45 Docker Container
14:00 Dockerhub
14:57 Практика. Пишем микросервис
17:30 Практика. Пишем dockerfile
23:25 Практика. Создаем docker образ
25:48 Практика. Запускам docke контейнер
27:19 Практика. Основные команды
30:00 Best practice. Как еще можно написать dockerfile
33:14 Best practice. Рекомендации
35:01 Итог
источник
👉@BookJava
⚡️👩💻 Хотите освоить Java с нуля и стать востребованным разработчиком? Это один из самых популярных языков программирования, который используется в крупных компаниях по всему миру.
🦾 Курс «Специализация: Java-разработчик» — это три ступени обучения, которые помогут вам пройти путь от новичка до востребованного Middle-разработчика. Вы научитесь создавать серверные приложения, работать с базами данных, осваивать Spring, Docker, Kubernetes и многое другое.
Обучение ведут практикующие эксперты, программа адаптирована для новичков, а диплом OTUS котируется в ведущих IT-компаниях.
Наш партнер — СберКорус, разработчик передовых цифровых решений!
Осталось всего несколько дней, чтобы записаться на курс и получить скидку.
👉 Успейте оставить заявку прямо сейчас: https://vk.cc/cKaEMl
Реклама. ООО «Отус онлайн-образование», ОГРН 1177746618576
Хранилище файлов. Java + WebDav
Java + WebDav - загружаем файл на webdav через Rest запрос.
00:00 Приветствие
00:34 Spring Init
00:55 Docker Hub
01:54 docker-compose
04:25 webdav.conf
06:00 application.yaml
06:50 Sardine
07:36 WebDavConfig
09:15 WebConfig
11:40 FileService
14:09 Controller
17:22 Docker Fix
17:47 Postman
18:16 что не так?
20:46 Подписывайтесь
источник
👉@BookJava
Совет💡: если ты обожаешь Ctrl + C и Ctrl + V, тебе точно понравится и Ctrl + W.
Это как выделение текста с помощью AI 😉
https://www.jetbrains.com/help/idea/working-with-source-code.html#editor_code_selection
👉@BookJava
🤝 Если код работает, это еще не значит, что он работает эффективно. Хотите разобраться, как ускорить приложения, найти утечки памяти и правильно деплоить их в облака?
🦾 На повышении квалификации «Java Developer. Advanced» вы изучите JVM на глубоком уровне, научитесь профилировать приложения, оптимизировать их под высокие нагрузки и выстраивать продвинутый мониторинг.
✔️ Глубокое погружение в устройство JVM
✔️ Практика с профилированием и трассировкой
✔️ Работа с Kubernetes, Prometheus и Grafana
✔️ Настройка метрик и логирования
Осталось несколько дней до закрытия набора.
➡️ Пройдите короткое тестирование для проверки своих навыков и присоединяйтесь к группе: https://vk.cc/cJT8Ny
🎁 Начните обучение со скидкой, подробности у менеджеров. ПРОМОКОД: JAVA_03
Реклама. ООО «Отус онлайн-образование», ОГРН 1177746618576
Совет Spring Framework💡
Вы можете инжектировать (autowire) бины, которые могут отсутствовать, обернув их в java.util.Optional. Таким образом вы сообщаете, что этот бин является необязательным, избегаете исключения, если он не существует, и можете аккуратно обработать его отсутствие с помощью Optional API.
👉@BookJava
Java 24 уже доступна!
Download Now: https://jdk.java.net/24/
Release notes: https://jdk.java.net/24/release-notes
API Javadoc: https://docs.oracle.com/en/java/javase/24/docs/api/index.html
Features: https://openjdk.org/projects/jdk/24/
Inside Java on JDK 24: https://inside.java/2025/03/18/the-arrival-of-java-24/
👉 @BookJava
👩💻 Создание приложения Блокнот на Java 👩💻
🗓 24 марта в 20:00 МСК
🆓 Бесплатно. Урок в рамках старта курса «Java-разработчик».
На вебинаре мы разработаем полноценное приложение «Блокнот» с графическим пользовательским интерфейсом, демонстрирующее базовые принципы создания текстового редактора на Java.
В процессе занятия мы реализуем такие функциональные возможности, как:
- создание нового текстового файла, его сохранение,
- загрузка уже существующего файла,
- редактирование текста, подсчет статистических данных и другие операции, характерные для текстовых редакторов.
Особое внимание будет уделено работе с файловой системой, потоками ввода/вывода и обработке событий, что позволит создать удобное и интуитивно понятное приложение.
Спикер Александр Фисунов — Senior Kotlin Developer в SSP Software на проекте ВТБ, опытный Java-разработчик и кандидат технических наук.
🔗 Ссылка на регистрацию: https://vk.cc/cJP0NY
Реклама. ООО «Отус онлайн-образование», ОГРН 1177746618576
#Java springboot
Совет: Нужно быстро собрать разрозненные данные в POST-запросе?
Просто создайте встроенную record в вашем @RestController и используйте её как @RequestBody.
Не нужно определять DTO в отдельном классе – record будет видна только внутри этого контроллера. 🚀
👉@BookJava
🧹 Как не захламлять логи в Java
Сегодня покажу вам простой, но важный приём: логируйте по уровню, а не по привычке.
Многие делают так:
log.info("User found: " + user);
user лежит целый граф сущностей с ленивыми загрузками, или список из тысячи записей. Вы просто убьёте читаемость логов и производительность.
if (log.isDebugEnabled()) {
log.debug("User found: {}", user);
}
log.debug("User found: id={}, email={}", user.getId(), user.getEmail());
INFO — для бизнес-событий (например, “заказ оформлен”)DEBUG — для отладкиWARN и ERROR — для проблем, которые требуют внимания
🧪 Зачем Java-разработчику тестировать логику в SQL?
Привет! Сегодня покажу вам полезный трюк для тех, кто пишет сложные запросы в PostgreSQL (или любом другом SQL-движке) и хочет их тестировать ещё до интеграции в Java-приложение.
Если у тебя в проекте сложная логика в JOIN, CASE, оконных функциях или CTE — протестируй это на стороне базы, как обычную функцию.
🔹 Создаём функцию в PostgreSQL:
CREATE OR REPLACE FUNCTION test_discount(user_id INT)
RETURNS NUMERIC AS $$
BEGIN
RETURN (
SELECT
CASE
WHEN u.vip = true THEN 0.2
ELSE 0.05
END
FROM users u WHERE u.id = user_id
);
END;
$$ LANGUAGE plpgsql;
SELECT test_discount(101); -- вернёт 0.2 или 0.05
pgTAP, например);
Сегодня я покажу вам простой, но мощный приём, который помогает упростить работу с коллекциями в Java — Collectors.collectingAndThen.
Если вы когда-нибудь писали что-то вроде:
List<String> list = someStream
.collect(Collectors.toList());
return Collections.unmodifiableList(list);
collectingAndThen сделает это в одну строку:
List<String> list = someStream.collect(
Collectors.collectingAndThen(
Collectors.toList(),
Collections::unmodifiableList
)
);
Optional, Set, Map, EnumMap и т.д.
Optional<String> maxName = people.stream()
.map(Person::getName)
.collect(Collectors.collectingAndThen(
Collectors.maxBy(Comparator.naturalOrder()),
Optional::ofNullable
));
Подборка Telegram каналов для программистов
/channel/bash_srv Bash Советы
/channel/win_sysadmin Системный Администратор Windows
/channel/lifeproger Жизнь программиста. Авторский канал.
/channel/devopslib Библиотека девопса | DevOps, SRE, Sysadmin
/channel/rabota1C_rus Вакансии для программистов 1С
Системное администрирование 📌
/channel/sysadmin_girl Девочка Сисадмин
/channel/srv_admin_linux Админские угодья
/channel/linux_srv Типичный Сисадмин
/channel/linux_odmin Linux: Системный администратор
/channel/devops_star DevOps Star (Звезда Девопса)
/channel/i_linux Системный администратор
/channel/linuxchmod Linux
/channel/sys_adminos Системный Администратор
/channel/tipsysdmin Типичный Сисадмин (фото железа, было/стало)
/channel/sysadminof Книги для админов, полезные материалы
/channel/i_odmin Все для системного администратора
/channel/i_odmin_book Библиотека Системного Администратора
/channel/i_odmin_chat Чат системных администраторов
/channel/i_DevOps DevOps: Пишем о Docker, Kubernetes и др.
/channel/sysadminoff Новости Линукс Linux
1C разработка 📌
/channel/odin1C_rus Cтатьи, курсы, советы, шаблоны кода 1С
/channel/DevLab1C 1С:Предприятие 8
Программирование C++📌
/channel/cpp_lib Библиотека C/C++ разработчика
/channel/cpp_knigi Книги для программистов C/C++
/channel/cpp_geek Учим C/C++ на примерах
Программирование Python 📌
/channel/pythonofff Python академия. Учи Python быстро и легко🐍
/channel/BookPython Библиотека Python разработчика
/channel/python_real Python подборки на русском и английском
/channel/python_360 Книги по Python Rus
Java разработка 📌
/channel/BookJava Библиотека Java разработчика
/channel/java_360 Книги по Java Rus
/channel/java_geek Учим Java на примерах
GitHub Сообщество 📌
/channel/Githublib Интересное из GitHub
Базы данных (Data Base) 📌
/channel/database_info Все про базы данных
Мобильная разработка: iOS, Android 📌
/channel/developer_mobila Мобильная разработка
/channel/kotlin_lib Подборки полезного материала по Kotlin
Фронтенд разработка 📌
/channel/frontend_1 Подборки для frontend разработчиков
/channel/frontend_sovet Frontend советы, примеры и практика!
/channel/React_lib Подборки по React js и все что с ним связано
Разработка игр 📌
/channel/game_devv Все о разработке игр
Библиотеки 📌
/channel/book_for_dev Книги для программистов Rus
/channel/programmist_of Книги по программированию
/channel/proglb Библиотека программиста
/channel/bfbook Книги для программистов
/channel/books_reserv Книги для программистов
БигДата, машинное обучение 📌
/channel/bigdata_1 Data Science, Big Data, Machine Learning, Deep Learning
Программирование 📌
/channel/bookflow Лекции, видеоуроки, доклады с IT конференций
/channel/coddy_academy Полезные советы по программированию
/channel/rust_lib Полезный контент по программированию на Rust
/channel/golang_lib Библиотека Go (Golang) разработчика
/channel/itmozg Программисты, дизайнеры, новости из мира IT
/channel/php_lib Библиотека PHP программиста 👨🏼💻👩💻
/channel/nodejs_lib Подборки по Node js и все что с ним связано
/channel/ruby_lib Библиотека Ruby программиста
QA, тестирование 📌
/channel/testlab_qa Библиотека тестировщика
Шутки программистов 📌
/channel/itumor Шутки программистов
Защита, взлом, безопасность 📌
/channel/thehaking Канал о кибербезопасности
/channel/xakep_2 Хакер Free
Книги, статьи для дизайнеров 📌
/channel/ux_web Статьи, книги для дизайнеров
Математика 📌
/channel/Pomatematike Канал по математике
/channel/phis_mat Обучающие видео, книги по Физике и Математике
Excel лайфхак📌
/channel/Excel_lifehack
/channel/tikon_1 Новости высоких технологий, науки и техники💡
/channel/mir_teh Мир технологий (Technology World)
Вакансии 📌
/channel/sysadmin_rabota Системный Администратор
/channel/progjob Вакансии в IT
🦾 Тест по Java 🦾
📌Пройдите тест из 20 вопросов и проверьте, насколько вы готовы к обучению на углубленном курсе «Java Developer. Professional» от OTUS.
Сможете сдать - пройдете на курс по спеццене!
👩💻 В программе курса — все актуальные инструменты, необходимые Middle+ разработчику на Java. Возможна рассрочка.
⏰ Время прохождения теста ограничено 30 минут
👉ПРОЙТИ ТЕСТ
Реклама. ООО «Отус онлайн-образование», ОГРН 1177746618576
📕 Открытый урок по разработке веб-приложений на Scala
На открытом уроке 1 апреля в 20:00 мск мы погрузимся в мир бэкенд-разработки на Scala.
📗 В результате вы:
— Узнаете ключевые аспекты создания современных веб-приложений на Scala;
— Познакомитесь с популярными фреймворками и инструментами для работы с базами данных;
— На практике создадите простое CRUD-приложение для закрепления навыков.
Спикер: Алексей Воронец — руководитель разработки департамента проектных решений и поисковых систем в компании Naumen, эксперт с 14-летним опытом, специализирующийся на Scala и функциональном программировании.
👉 Регистрируйтесь прямо сейчас, чтобы не пропустить мероприятие
https://vk.cc/cKbqwh
Реклама. ООО «Отус онлайн-образование», ОГРН 1177746618576
Пишем рекомендательную систему музыки на Java
Андрей Кузнецов — Мастер-класс
Машинное обучение обычно рассматривают как отдельно стоящую область, требующую специфических знаний. Однако на практике бывает, что для решения бизнес-задач может быть достаточно и простых решений, имплементация которых не представляет сложностей для разработчика.
Используя открытый датасет, мы пишем с нуля на Java рекомендательную систему музыки и разберем, какие из наивных решений могут не сработать в реальных системах. На примере технологий Одноклассников спикер рассказывает, как решаются ML-задачи в гетерогенных продакшенах, где необходимо использовать вместе Java и Python.
Мастер-класс будет интересен разработчикам, которым интересна тема машинного обучения, но они либо еще не погружались в нее, либо сделали самые первые шаги.
источник
👉@BookJava
🔧 Как ускорить сборку Maven проекта в 3 раза
Сегодня покажу пару приёмов, которые помогут тебе значительно ускорить сборку Maven проекта. Особенно полезно, если ты работаешь с большими монолитами или частыми CI/CD прогонками.
🚀 1. Включи параллельную сборку
Добавь флаг -T (thread count), чтобы Maven собирал модули параллельно:
mvn clean install -T 1C
1C — это количество потоков = количеству ядер CPU. Можешь указать, например, -T 4 для 4 потоков. Эффект — сборка может стать в 2–4 раза быстрее.
mvn clean install -DskipTests
-DskipTests — пропускает *и* компиляцию тестов, и сами тесты.
mvn clean install -Dmaven.test.skip=false -DskipTests=true
mvn dependency:go-offline
mvn dependency:go-offline
👩💻 Rate-limiter. Bucket4j
Приглашаем на открытый урок.
🗓 24 марта в 20:00 МСК
🆓 Бесплатно. Урок в рамках старта курса «Java Developer. Professional».
Продолжаем изучать библиотеки обеспечения устойчивости приложений. На примере Bucket4j посмотрим устройство распределенного Rate-limiter-а.
О чём поговорим:
✔️ Познакомимся с библиотекой Bucket4j.
✔️ Узнаем основные принципы действия и сценарии применения.
Кому будет интересно:
Вебинар будет полезен Java-разработчикам, архитекторам ПО и инженерам по устойчивости систем, заинтересованным в эффективном управлении потоками запросов и защите приложений от перегрузок.
🔗 Ссылка на регистрацию: https://vk.cc/cJUU0G
Реклама. ООО «Отус онлайн-образование», ОГРН 1177746618576
Что такое synchronized?это ключевое слово в Java, которое используется для управления доступом к критическим секциям кода при многопоточном выполнении. Оно гарантирует, что только один поток может выполнить блок кода или метод в определённый момент времени.
synchronized —
Зачем нужен synchronized?
Когда несколько потоков обращаются к общим данным (например, к переменной, коллекции, объекту), может возникнуть состояние гонки (race condition), приводящее к некорректной работе программы. Чтобы этого избежать, и используется synchronized.
Как работает?synchronized блокирует объект или класс, чтобы другие потоки не могли войти в синхронизированную секцию, пока текущий поток её не покинет.
Примеры
🔹 Синхронизация метода (экземпляра):
public synchronized void increment() {
count++;
}
public void increment() {
synchronized (this) {
count++;
}
}
public static synchronized void increment() {
staticCount++;
}
synchronized (MyClass.class) {
staticCount++;
}
synchronized влияет на производительность, т.к. вызывает блокировки.java.util.concurrent.locks.Lock или атомарные классы (AtomicInteger и т.д.).
📌 Почему Optional не стоит использовать в качестве параметра метода?
Сегодня разберем один из популярных вопросов: можно ли использовать Optional в параметрах метода? Казалось бы, это удобный способ передавать необязательный аргумент, но есть нюансы.
🚫 Почему это плохая практика?
1️⃣ Усложнение API
Когда метод принимает Optional, это вынуждает вызывающий код создавать Optional.of(value), даже если он не использует Optional в своем контексте. Это добавляет лишнюю работу.
2️⃣ Неявность кода
Если метод принимает Optional, становится неясно, можно ли просто передать null или обязательно использовать Optional.empty().
3️⃣ Снижение читаемости и удобства
Обычное условие if (param != null) проще и понятнее, чем if (param.isPresent()).
4️⃣ Не поддерживается стандартом Java API
В JDK не встретишь API, где Optional используется как параметр метода. Это не случайность — так принято по соглашению.
✅ Как правильно?
Используйте обычные перегруженные методы или @Nullable аннотацию:
public void process(String value) {
// обработка значения
}
public void process() {
process("default");
}
null, то лучше явно работать с null, чем принудительно оборачивать его в Optional.
👩💻 Открытый урок «DAO на Spring JDBC»
🗓 26 марта в 20:00 МСК
🆓 Бесплатно. Урок в рамках старта курса «Разработчик на Spring Framework»
Использование нативного SQL с Spring JDBC позволяет создать безопасное, поддерживаемое и тестируемое DAO для эффективного доступа к данным.
О чём поговорим:
- Преимущества нативного SQL при разработке DAO.
- Основные возможности Spring JDBC для работы с запросами.
- Подходы к обеспечению безопасности и тестируемости DAO.
🔗 Ссылка на регистрацию: https://vk.cc/cJRacK
Реклама. ООО «Отус онлайн-образование», ОГРН 1177746618576
🛠️ SOLID: Почему важно соблюдать принципы?
Сегодня поговорим о SOLID – пяти принципах, которые делают код понятным, гибким и легким для поддержки. Если ты хочешь писать код, который не треснет по швам через пару месяцев, эти принципы — твои лучшие друзья.
1. Single Responsibility Principle (SRP)
Одна ответственность – один класс.
Если у класса больше одной причины измениться, значит, он нарушает SRP. Такой код сложно поддерживать, потому что при изменении одной логики мы можем случайно сломать другую.
✅ Правильно:
class ReportGenerator {
void generateReport() { /* Логика генерации отчета */ }
}
class ReportSaver {
void saveReport() { /* Логика сохранения отчета */ }
}
class ReportService {
void generateAndSaveReport() { /* Генерация + сохранение отчета */ }
}
interface Payment {
void process();
}
class CreditCardPayment implements Payment {
public void process() { /* Логика оплаты картой */ }
}
class PayPalPayment implements Payment {
public void process() { /* Логика оплаты PayPal */ }
}
class Bird {
void fly() { /* Летает */ }
}
class Penguin extends Bird {
void fly() { throw new UnsupportedOperationException("Пингвины не летают!"); }
}
Penguin нарушает контракт родителя.
interface Bird { }
interface FlyingBird extends Bird { void fly(); }
class Sparrow implements FlyingBird {
public void fly() { /* Летает */ }
}
class Penguin implements Bird {
// Пингвин вообще не имеет метода fly()
}
interface Worker {
void work();
void eat();
}
class Robot implements Worker {
public void work() { /* Работает */ }
public void eat() { throw new UnsupportedOperationException("Роботы не едят!"); }
}
interface Workable {
void work();
}
interface Eatable {
void eat();
}
class Robot implements Workable {
public void work() { /* Работает */ }
}
class Lamp {
void turnOn() { /* Включить */ }
}
class Switch {
private Lamp lamp;
Switch(Lamp lamp) {
this.lamp = lamp;
}
void press() { lamp.turnOn(); }
}
interface Switchable {
void turnOn();
}
class Lamp implements Switchable {
public void turnOn() { /* Включить */ }
}
class Switch {
private Switchable device;
Switch(Switchable device) {
this.device = device;
}
void press() { device.turnOn(); }
}
🚀 Совет по Spring API 🚀
LocaleContextHolder
Стратегия для хранения текущей локали потокобезопасным способом. Полезно для получения текущей локали без необходимости передавать её явно через параметры методов. 🔥
https://docs.spring.io/spring-framework/docs/current/javadoc-api/org/springframework/context/i18n/LocaleContextHolder.html
👉@BookJava
📌 Stream API: Группировка данных в Java
Привет, друзья! Сегодня разберем мощную возможность Stream API – группировка данных с помощью Collectors.groupingBy(). Это отличный инструмент, когда нужно собирать элементы в группы по какому-то признаку.
📌 Как это работает?
Метод groupingBy используется в Collectors и позволяет группировать элементы по ключу, который мы указываем. Давайте рассмотрим на примере:
import java.util.*;
import java.util.stream.Collectors;
class Person {
String name;
String city;
Person(String name, String city) {
this.name = name;
this.city = city;
}
@Override
public String toString() {
return name;
}
}
public class GroupingExample {
public static void main(String[] args) {
List<Person> people = List.of(
new Person("Иван", "Москва"),
new Person("Анна", "Санкт-Петербург"),
new Person("Сергей", "Москва"),
new Person("Мария", "Казань"),
new Person("Алексей", "Санкт-Петербург")
);
Map<String, List<Person>> groupedByCity = people.stream()
.collect(Collectors.groupingBy(person -> person.city));
groupedByCity.forEach((city, residents) ->
System.out.println(city + ": " + residents)
);
}
}
people с объектами Person, у которых есть name и city. groupingBy, передавая person -> person.city в качестве критерия группировки. Map<String, List<Person>>, где ключ – город, а значение – список людей из этого города. forEach.
Москва: [Иван, Сергей]
Санкт-Петербург: [Анна, Алексей]
Казань: [Мария]
groupingBy() – это универсальный инструмент, который решает такие задачи.
Map<String, Long> countByCity = people.stream()
.collect(Collectors.groupingBy(p -> p.city, Collectors.counting()));
Map<String, Set<String>> namesByCity = people.stream()
.collect(Collectors.groupingBy(p -> p.city,
Collectors.mapping(p -> p.name, Collectors.toSet())));