Временная сложность — это оценка времени выполнения алгоритма в зависимости от размера входных данных. Измеряется через нотацию O(...) и помогает сравнивать эффективность алгоритмов.
Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍15🤔1
COMMIT – это команда в SQL, которая фиксирует (сохраняет) изменения, сделанные внутри транзакции. После выполнения COMMIT изменения становятся постоянными и их уже нельзя отменить. Простой пример использования
COMMITBEGIN TRANSACTION;
UPDATE accounts SET balance = balance - 100 WHERE id = 1;
UPDATE accounts SET balance = balance + 100 WHERE id = 2;
COMMIT; -- Сохраняем изменения
Что будет, если НЕ выполнить
COMMIT? BEGIN TRANSACTION;
UPDATE users SET age = 30 WHERE id = 1;
COMMIT vs ROLLBACK BEGIN TRANSACTION;
UPDATE orders SET status = 'CANCELLED' WHERE id = 10;
ROLLBACK; -- ОТМЕНЯЕМ изменения, данные не меняются
Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍8💊1
Согласно контракту:
- obj.equals(null) должен возвращать false, не NullPointerException.
Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
🔥16👍10💊5
Spring и Spring Boot являются частью экосистемы, которая предоставляет широкий спектр инструментов для разработки современных Java-приложений. Несмотря на тесную связь, между ними есть ключевые отличия.
Это мощный и широко используемый фреймворк для разработки приложений на Java. Он предоставляет обширный набор функциональностей, включая инверсию управления (IoC) и внедрение зависимостей (DI), абстракции для работы с транзакциями, обработку исключений, поддержку аспектно-ориентированного программирования (AOP) и многое другое. Он предназначен для упрощения Java EE разработки, обеспечивая легкость создания масштабируемых и легко поддерживаемых приложений.
С другой стороны, представляет собой расширение Spring Framework, предназначенное для упрощения процесса конфигурации и развертывания Spring-приложений. Он автоматизирует многие процессы, предоставляя "готовые к использованию" настройки для быстрого старта проектов и избавления от необходимости вручную определять стандартную конфигурацию.
Spring Framework предоставляет основу для создания приложений на Java, в то время как Spring Boot предлагает конвенции и автоматическую конфигурацию для быстрого старта и развертывания приложений.
В Spring для настройки приложения часто требуется детальная конфигурация, включая XML-файлы или аннотации. Spring Boot стремится уменьшить эту сложность, автоматически конфигурируя компоненты на основе добавленных в проект зависимостей.
Spring Boot по умолчанию включает в себя встроенный сервер приложений, что упрощает развертывание и тестирование веб-приложений.
Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍12💊2
По умолчанию equals() сравнивает ссылки (т.е. адреса в памяти).
Если не переопределить:
- Два объекта с одинаковыми значениями будут считаться разными.
- Set, Map могут работать неправильно (например, хранить дубликаты).
Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍13🔥1
В программировании существует множество видов тестирования, которые можно разделить на категории по уровню тестирования, методам выполнения и целям. Вот основные виды:
Тестирование отдельных методов или классов.
Цель: Проверить работу минимальных компонентов программы.
Инструменты: JUnit, TestNG.
@Test
public void testAddition() {
assertEquals(5, Calculator.add(2, 3));
}
Тестирование взаимодействия между модулями.
Цель: Убедиться, что модули правильно работают вместе.
Пример: Проверка взаимодействия сервиса и базы данных.
Инструменты: Spring Test, Apache Camel Test.
Проверка всей системы как единого целого.
Цель: Убедиться, что все компоненты работают вместе и система соответствует требованиям.
Проводится с участием клиента или конечных пользователей.
Цель: Убедиться, что система удовлетворяет бизнес-требованиям.
Тесты выполняются вручную.
Цель: Найти ошибки, которые может не уловить автоматизация.
Пример: Тестировщик вручную проверяет пользовательский интерфейс.
Тесты выполняются автоматически с использованием скриптов и инструментов.
Цель: Снизить время и затраты на повторяющиеся тесты.
Инструменты: Selenium, JUnit, Appium.
Проверяет, что функции системы работают как ожидалось.
Цель: Убедиться в соответствии требованиям.
Инструменты: Selenium, Postman.
Тестирование производительности (Performance Testing): Проверяет скорость, отклик и стабильность.
Инструменты: JMeter, Gatling.
Тестирование безопасности (Security Testing): Проверяет защиту системы.
Инструменты: OWASP ZAP, Burp Suite.
Тестирование удобства использования (Usability Testing): Проверяет интерфейс на удобство для пользователя.
Быстрая проверка работоспособности ключевых функций.
Цель: Убедиться, что основные функции работают, прежде чем углубляться в тесты.
Проверяет, что новые изменения не сломали старую функциональность.
Цель: Убедиться, что баги, исправленные ранее, не повторились.
Проверяет систему без знаний о внутреннем устройстве.
Цель: Оценить функциональность с точки зрения пользователя.
Проверяет систему с учетом внутренней структуры кода.
Цель: Оценить корректность логики программы.
Проверяет, какая версия системы лучше (например, два варианта интерфейса).
Цель: Повысить пользовательский опыт.
Проверяет, как система работает под большой нагрузкой.
Инструменты: Apache JMeter.
Проверяет, как система работает в условиях сверхвысокой нагрузки.
Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍12
Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍10💊3
Каждый бин (компонент) проходит через жизненный цикл, который начинается с его создания и заканчивается уничтожением. Этот цикл включает в себя ряд этапов, на которых он предоставляет различные точки для настройки поведения бина. Вот основные этапы жизненного цикла:
Создает экземпляр бина из класса определения бина.
Внедряет значения и ссылки на другие бины в свойства текущего бина, используя конфигурацию, заданную в XML, аннотациях или конфигурации.
Если бин реализует один из Aware интерфейсов, он вызывает соответствующие методы, передавая экземпляру бина ссылку на контекст, фабрику бинов и т.д.
Перед инициализацией бина, он дает возможность BeanPostProcessor'ам обработать объект. Это может быть использовано для проксирования бинов или для иной предварительной обработки.
Если для бина определен метод инициализации (через аннотацию
@PostConstruct, интерфейс InitializingBean или атрибут init-method в XML-конфигурации), он вызывает его после того, как все свойства бина были установлены.После вызова метода инициализации бин полностью инициализирован и готов к использованию в приложении.
Когда контекст приложения закрывается, и бины должны быть уничтожены, он вызывает метод уничтожения для бинов, которые определяют его (через аннотацию
@PreDestroy, интерфейс DisposableBean или атрибут destroy-method в XML-конфигурации).Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍11
Интеграционное тестирование проверяет взаимодействие компонентов приложения: слоёв, сервисов, БД, API. В Spring его реализуют через аннотации
Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
🔥8👍2💊1
Метод
intern() в классе String используется для оптимизации памяти. Он добавляет строку в String Pool и возвращает её ссылку, если строка уже там есть.
Без
intern() – строки создаются в Heap (куче) String s1 = new String("Hello"); // В куче (Heap)
String s2 = new String("Hello");
System.out.println(s1 == s2); // false (разные объекты)С
intern() – строки хранятся в String Pool String s1 = new String("Hello").intern();
String s2 = new String("Hello").intern();
System.out.println(s1 == s2); // true (одна строка в String Pool)Это специальная область памяти, где хранятся уникальные строковые литералы.
Все строковые литералы (
"Hello") по умолчанию хранятся в String Pool. String s1 = "Hello"; // В String Pool
String s2 = "Hello"; // Ссылается на тот же объект
System.out.println(s1 == s2); // true
Когда у вас много одинаковых строк в памяти (например, имена, идентификаторы).
Для экономии памяти, если строки часто дублируются.
В парсинге JSON, XML – одни и те же строки могут повторяться тысячи раз.
List<String> names = new ArrayList<>();
for (int i = 0; i < 100000; i++) {
names.add(("User" + (i % 100)).intern()); // Используем String Pool
}
Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍9
Hibernate использует два уровня кэша:
- 1 уровень (Session Cache) — встроен по умолчанию, работает в рамках одного Session. Каждый объект, загруженный из базы, кешируется на время сессии.
- 2 уровень (SessionFactory Cache) — опциональный, хранит объекты между сессиями. Реализуется через сторонние решения (Ehcache, Infinispan, Hazelcast).
- Также есть Query Cache — кеширует результаты запросов HQL.
Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
🔥15👍4
Когда вы переопределяете методы
equals() и hashCode(), важно соблюдать контракт, иначе объект может вести себя некорректно в коллекциях (HashMap, HashSet и др.). Метод
equals() определяет, когда два объекта равны. Рефлексивность –
x.equals(x) всегда true. Симметричность –
x.equals(y) == y.equals(x). Транзитивность – если
x.equals(y) и y.equals(z), то x.equals(z). Согласованность – многократные вызовы
x.equals(y) дают один и тот же результат. Сравнение с
null всегда false – x.equals(null) == false. class Person {
private String name;
private int age;
public Person(String name, int age) {
this.name = name;
this.age = age;
}
@Override
public boolean equals(Object obj) {
if (this == obj) return true; // Проверка на одинаковые ссылки
if (obj == null || getClass() != obj.getClass()) return false; // Проверка типа
Person person = (Person) obj;
return age == person.age && name.equals(person.name); // Сравнение полей
}
}Метод
hashCode() возвращает числовой хеш-код объекта. Он должен соответствовать equals()! Если
x.equals(y) == true, то x.hashCode() == y.hashCode(). Если
x.hashCode() != y.hashCode(), то x.equals(y) == false (но обратное не всегда верно). Хеш-код должен оставаться неизменным, если объект не изменяется.
@Override
public int hashCode() {
return Objects.hash(name, age);
}
В коллекциях, таких как
HashSet, HashMap, HashTable, объекты хранятся по хеш-коду. Что будет, если
equals() переопределён, но hashCode() – нет? Set<Person> people = new HashSet<>();
people.add(new Person("Иван", 25));
people.add(new Person("Иван", 25)); // Ожидаем, что не добавится
System.out.println(people.size()); // ❌ Будет 2, а не 1, если `hashCode()` отсутствует!
Правильный вариант (
equals() + hashCode()) class Person {
private String name;
private int age;
public Person(String name, int age) {
this.name = name;
this.age = age;
}
@Override
public boolean equals(Object obj) {
if (this == obj) return true;
if (obj == null || getClass() != obj.getClass()) return false;
Person person = (Person) obj;
return age == person.age && name.equals(person.name);
}
@Override
public int hashCode() {
return Objects.hash(name, age);
}
}Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍11
Да, начиная с Java 7, поддерживается switch(String). Компилятор оптимизирует это через хеш-коды и сравнение строк.
Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍17🔥3
REST – это удобный и популярный архитектурный стиль, но в высоконагруженных системах у него есть недостатки.
Проблема: Каждый REST-запрос передаёт много мета-информации (заголовки, cookies, CORS, JSON/XML).
GET /users/123 HTTP/1.1
Host: api.example.com
Authorization: Bearer token123
Content-Type: application/json
В WebSocket/gRPC запрос выглядел бы так
{ "userId": 123 }Проблема: REST использует "запрос-ответ", но **не поддерживает real-time.
Что происходит в REST?
1. Клиент делает HTTP-запрос к серверу.
2. Сервер обрабатывает и отправляет ответ.
3. Если клиенту нужно новое сообщение, он снова делает запрос (Polling) или использует Long Polling.
Проблема: Не все REST-запросы можно кэшировать.
Кэшируются только
GET-запросы (если сервер поддерживает ETag и Cache-Control). POST, PUT, DELETE – не кэшируются, потому что меняют данные. Проблема: REST требует много отдельных запросов, если нужно загрузить связанные данные.
Пример проблемы REST:
Получить пользователя:
/users/123 Получить заказы этого пользователя:
/users/123/orders Получить детали заказов:
/orders/456/detailsСтавь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍12
- static поля не сериализуются, потому что принадлежат классу, а не экземпляру;
- final поля сериализуются как обычно, если они не static.
Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍8🔥2
Поверхностное копирование (Shallow Copy) – это процесс создания нового объекта, который содержит ссылки на те же вложенные объекты, что и оригинал.
Способ 1: Метод
clone() (реализация Cloneable) class Person implements Cloneable {
String name;
public Person(String name) {
this.name = name;
}
@Override
protected Object clone() throws CloneNotSupportedException {
return super.clone(); // Поверхностное копирование
}
}
public class Main {
public static void main(String[] args) throws CloneNotSupportedException {
Person original = new Person("Иван");
Person copy = (Person) original.clone();
System.out.println(copy.name); // Иван
}
}Если объект содержит вложенные объекты, они не копируются, а передаются по ссылке.
class Address {
String city;
public Address(String city) { this.city = city; }
}
class User implements Cloneable {
String name;
Address address;
public User(String name, Address address) {
this.name = name;
this.address = address;
}
@Override
protected Object clone() throws CloneNotSupportedException {
return super.clone(); // Поверхностное копирование
}
}
public class Main {
public static void main(String[] args) throws CloneNotSupportedException {
Address address = new Address("Москва");
User original = new User("Иван", address);
User copy = (User) original.clone();
copy.address.city = "Санкт-Петербург"; // Меняем адрес у копии
System.out.println(original.address.city); // Санкт-Петербург (изменилось и у оригинала!)
}
}Решение: Создать новый вложенный объект в
clone() @Override
protected Object clone() throws CloneNotSupportedException {
User clonedUser = (User) super.clone();
clonedUser.address = new Address(this.address.city); // Копируем вложенный объект
return clonedUser;
}
Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍11
Это реализация Set, основанная на хеш-таблице, которая:
- не допускает дубликатов;
- не сохраняет порядок;
- обеспечивает быстрые операции добавления, удаления и поиска (O(1)).
Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍16🔥1
В Java существуют несколько подходов для чтения XML-файлов, каждый из которых имеет свои преимущества и недостатки.
XML-файл загружается целиком в память в виде древовидной структуры. Разработчик может работать с узлами (nodes), элементами (elements) и атрибутами (attributes) через API.
import org.w3c.dom.*;
import javax.xml.parsers.*;
public class DomExample {
public static void main(String[] args) throws Exception {
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
DocumentBuilder builder = factory.newDocumentBuilder();
Document doc = builder.parse("example.xml");
NodeList nodeList = doc.getElementsByTagName("element");
for (int i = 0; i < nodeList.getLength(); i++) {
Element element = (Element) nodeList.item(i);
System.out.println(element.getTextContent());
}
}
}
XML обрабатывается построчно (по событиям). При чтении вызываются методы обработчика событий (например, начало элемента, конец элемента).
import org.xml.sax.*;
import org.xml.sax.helpers.DefaultHandler;
import javax.xml.parsers.SAXParser;
import javax.xml.parsers.SAXParserFactory;
public class SaxExample {
public static void main(String[] args) throws Exception {
SAXParserFactory factory = SAXParserFactory.newInstance();
SAXParser parser = factory.newSAXParser();
parser.parse("example.xml", new DefaultHandler() {
public void startElement(String uri, String localName, String qName, Attributes attributes) {
System.out.println("Start Element: " + qName);
}
public void characters(char[] ch, int start, int length) {
System.out.println("Text: " + new String(ch, start, length));
}
public void endElement(String uri, String localName, String qName) {
System.out.println("End Element: " + qName);
}
});
}
}
XML обрабатывается как поток, но предоставляет больше контроля, чем SAX. Поддерживает чтение и запись.
import javax.xml.stream.*;
import java.io.FileReader;
public class StaxExample {
public static void main(String[] args) throws Exception {
XMLInputFactory factory = XMLInputFactory.newInstance();
XMLStreamReader reader = factory.createXMLStreamReader(new FileReader("example.xml"));
while (reader.hasNext()) {
int event = reader.next();
if (event == XMLStreamReader.START_ELEMENT) {
System.out.println("Start Element: " + reader.getLocalName());
} else if (event == XMLStreamReader.CHARACTERS) {
System.out.println("Text: " + reader.getText().trim());
} else if (event == XMLStreamReader.END_ELEMENT) {
System.out.println("End Element: " + reader.getLocalName());
}
}
}
}
Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍11
- execute(Runnable) просто передает задачу на выполнение без возвращаемого результата.
- submit(Callable/Runnable) возвращает объект Future, который можно использовать для отслеживания выполнения и получения результата задачи.
Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍10🔥8
Inversion of Control (IoC) — это принцип проектирования, при котором управление созданием и жизненным циклом объектов передаётся внешней системе.
Без IoC код сильно зависит от конкретных классов, что усложняет тестирование и поддержку.
class Car {
private Engine engine;
public Car() {
this.engine = new Engine(); // Прямое создание зависимости ❌
}
}С IoC (зависимость передаётся извне)
class Car {
private final Engine engine;
public Car(Engine engine) { // Зависимость передаётся через конструктор
this.engine = engine;
}
}IoC достигается через паттерны проектирования, такие как:
Dependency Injection (DI) – передача зависимостей извне (через конструктор, поле или метод).
Factory Method – создание объектов через фабрики.
Event-driven подход – реакция на события вместо явного вызова методов.
Spring реализует IoC через контейнер IoC, который управляет созданием объектов (бинов) и их зависимостями.
@Component
class Engine {}
@Component
class Car {
private final Engine engine;
@Autowired
public Car(Engine engine) { // Spring автоматически передаст нужный объект
this.engine = engine;
}
}
Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍10