7Какие четыре принципа ООП поддерживает Java?
Java поддерживает encapsulation, abstraction, inheritance и polymorphism. Encapsulation скрывает внутреннее состояние за public API. Abstraction выделяет существенное поведение. Inheritance создает новый тип на основе существующего. Polymorphism позволяет работать с разными реализациями через общий contract. На практике composition часто предпочтительнее inheritance, потому что дает меньшую связанность.
interface PaymentService {
void pay(BigDecimal amount);
}
class CardPaymentService implements PaymentService {
@Override
public void pay(BigDecimal amount) {
// payment implementation
}
}
8Чем перегрузка метода отличается от переопределения?
Overloading — несколько методов с одним именем, но разными параметрами; выбор делается компилятором по static types аргументов. Overriding — subclass заменяет реализацию instance method parent class; выбор делается runtime по фактическому типу объекта. Static methods не переопределяются, а скрываются; private methods не переопределяются, потому что не наследуются как доступные members.
void send(String message) {}
void send(String message, int priority) {}
class Animal {
void speak() { System.out.println("Animal"); }
}
class Dog extends Animal {
@Override
void speak() { System.out.println("Dog"); }
}
9Чем interface отличается от abstract class?
Interface задает contract и может содержать abstract methods, default methods, static methods, constants и private helpers. Abstract class может дополнительно иметь instance state, constructors, protected fields, common implementation и abstract/concrete methods. Класс может extend только один class, но implement несколько interfaces. Interface лучше для независимого contract, abstract class — для близких типов с общей реализацией и состоянием.
interface Repository<T> {
Optional<T> findById(long id);
}
10Что означает ключевое слово final?
final variable можно присвоить только один раз, но final reference не делает объект immutable. final method нельзя override. final class нельзя extend. final выражает намерение и ограничивает изменение ссылки или наследование, но сам по себе не обеспечивает полноценную immutable model или thread safety.
final int maxAttempts = 3;
final List<String> names = new ArrayList<>();
names.add("Alice"); // allowed
public final void validate() {}
public final class Token {}
11Что такое record и когда его следует использовать?
Record — компактный способ объявить data carrier. Компилятор создает private final fields, accessors, constructor, equals, hashCode и toString. Records final и хорошо подходят для DTO, commands, events, calculation results, keys и values. Record дает shallow immutability: если компонент содержит mutable list, сам list все еще можно изменить, поэтому нужен defensive copy.
public record User(long id, String name) {}
public record Order(List<String> items) {
public Order {
items = List.copyOf(items);
}
}
12Что такое immutable object и как его создать?
Immutable object не меняет наблюдаемое состояние после создания. Обычно class делают final, fields — private final, setters не предоставляют, состояние полностью инициализируют в constructor и не раскрывают mutable internals. Для mutable inputs и outputs используют defensive copies. Immutable objects проще анализировать, безопаснее использовать как map keys и легче разделять между threads.
public final class User {
private final String name;
private final List<String> roles;
public User(String name, List<String> roles) {
this.name = name;
this.roles = List.copyOf(roles);
}
public List<String> getRoles() {
return roles;
}
}