0Pricing
Java Academy · Урок

Оператор instanceof

Используйте instanceof, чтобы проверить типы объектов перед приведением и избежать ClassCastException.

«Оператор instanceof» — бесплатный урок Java Academy на CoddyKit. Это урок 3 из 4. Ты можешь прочитать весь урок бесплатно ниже — а потом практиковать его прямо в браузере с встроенным редактором кода и ИИ-репетитором 24/7. Это часть пути обучения Java Academy, и твой прогресс синхронизируется между веб-версией и приложением CoddyKit. Курс Java Academy содержит 4 уроков всего.

Оператор проверки типа

Оператор instanceof проверяет, является ли объект экземпляром указанного типа во время выполнения. Он возвращает true или false и предотвращает ClassCastException до приведения типа.

Базовое использование проверки типа

Используйте instanceof, чтобы проверить тип объекта во время выполнения перед безопасным приведением типа.

Object obj = "Hello, Java!";

if (obj instanceof String) {
    String s = (String) obj;
    System.out.println(s.toUpperCase()); // HELLO, JAVA!
}

Object num = Integer.valueOf(42);
System.out.println(num instanceof Integer); // true
System.out.println(num instanceof String);  // false

Проверка типа при наследовании

instanceof возвращает true, если объект является экземпляром класса или любого подкласса (либо любого интерфейса, который реализует класс).

class Animal {}
class Dog extends Animal {}
class Cat extends Animal {}

Animal a = new Dog();

System.out.println(a instanceof Animal); // true
System.out.println(a instanceof Dog);    // true
System.out.println(a instanceof Cat);    // false

Сопоставление с образцом при проверке типа (Java 16+)

В Java 16 появилось сопоставление с образцом для instanceof: можно объявить переменную привязки в том же выражении, устранив явное приведение типа.

Object shape = "circle";

// Old way
if (shape instanceof String) {
    String s = (String) shape;
    System.out.println(s.length());
}

// New way (Java 16+) — binding variable 's' is in scope
if (shape instanceof String s) {
    System.out.println(s.length()); // 6
}

Сопоставление с образцом в методе

Сопоставление с образцом делает выбор действий по типу чистым и безопасным. Переменная привязки доступна только в той области действия, где условие заведомо истинно.

sealed interface Shape permits Circle, Rectangle {}
record Circle(double radius) implements Shape {}
record Rectangle(double width, double height) implements Shape {}

static double area(Shape s) {
    if (s instanceof Circle c) {
        return Math.PI * c.radius() * c.radius();
    } else if (s instanceof Rectangle r) {
        return r.width() * r.height();
    }
    throw new IllegalArgumentException("Unknown shape");
}

System.out.println(area(new Circle(5)));         // 78.53...
System.out.println(area(new Rectangle(4, 6)));   // 24.0

Проверка типа для пустой ссылки

null instanceof AnyType всегда возвращает false — исключение не возникает. Поэтому instanceof безопасно использовать для проверки перед приведением типа.

String s = null;
System.out.println(s instanceof String); // false (not NPE)

Object o = null;
if (o instanceof Number n) {
    System.out.println(n.intValue());
} else {
    System.out.println("Not a number (or null)"); // prints this
}

Выражения выбора и сопоставление с образцом

В Java 21 сопоставление с образцом было расширено на выражения выбора, что позволяет выполнять маршрутизацию по типу без цепочек условных конструкций.

static String describe(Object obj) {
    return switch (obj) {
        case Integer i -> "Integer: " + i;
        case Double d  -> "Double: " + d;
        case String s  -> "String of length " + s.length();
        case null      -> "null value";
        default        -> "Unknown: " + obj.getClass().getSimpleName();
    };
}

System.out.println(describe(42));       // Integer: 42
System.out.println(describe(3.14));     // Double: 3.14
System.out.println(describe("hello")); // String of length 5
System.out.println(describe(null));     // null value

ClassCastException без проверки типа

Приведение без предварительной проверки приводит к ClassCastException во время выполнения — это распространённая ошибка в устаревшем коде, которую помогает предотвращать сопоставление с образцом.

Object obj = "I am a String";

try {
    Integer i = (Integer) obj; // ClassCastException!
} catch (ClassCastException e) {
    System.out.println("Cannot cast String to Integer");
}

// Safe version
if (obj instanceof Integer i) {
    System.out.println("Is integer: " + i);
} else {
    System.out.println("Not an integer");
}

Практика: обработка смешанного списка

Практический пример: обработка разнородного списка объектов с помощью сопоставления с образцом.

import java.util.List;

List<Object> events = List.of(
    "User login", 42, 3.14, "Payment processed", 100
);

double numericSum = 0;
for (Object e : events) {
    if (e instanceof Integer n) numericSum += n;
    else if (e instanceof Double d) numericSum += d;
    else if (e instanceof String s) System.out.println("Log: " + s);
}
System.out.printf("Numeric sum: %.2f%n", numericSum); // 145.14

Запечатанные классы и исчерпывающее сопоставление

Запечатанные классы (Java 17+) ограничивают набор классов, которые могут их расширять. В сочетании с выражением выбора и сопоставлением с образцом компилятор может проверить полноту обработки — ветка по умолчанию не нужна.

sealed interface Notification permits EmailNotification, SmsNotification {}
record EmailNotification(String to, String body) implements Notification {}
record SmsNotification(String phone, String text) implements Notification {}

static void send(Notification n) {
    switch (n) {
        case EmailNotification e ->
            System.out.println("Email to " + e.to() + ": " + e.body());
        case SmsNotification s ->
            System.out.println("SMS to " + s.phone() + ": " + s.text());
        // no default needed — compiler knows all cases are covered
    }
}

Шаблоны с условиями

Сопоставление с образцом поддерживает защитные условия с помощью when (Java 21), позволяя добавлять логические условия к проверкам типа.

static String classify(Number n) {
    return switch (n) {
        case Integer i when i < 0  -> "negative int: " + i;
        case Integer i when i == 0 -> "zero";
        case Integer i             -> "positive int: " + i;
        case Double d              -> "double: " + d;
        default                    -> "other number";
    };
}

System.out.println(classify(-5));  // negative int: -5
System.out.println(classify(0));   // zero
System.out.println(classify(7));   // positive int: 7

Быстрая проверка

Что возвращает следующее выражение?

Object obj = null;
boolean result = obj instanceof String;
System.out.println(result);

Итоги: оператор проверки типа

Основные выводы:

  • Оператор проверки типа проверяет тип во время выполнения и предотвращает ClassCastException
  • Для пустой ссылки возвращает ложное значение — NPE не возникает
  • Возвращает истинное значение для самого класса и всех его подклассов и интерфейсов
  • В Java 16+ сопоставление с образцом объединяет проверку и приведение типа в одном выражении
  • В Java 21 выражение выбора с образцами выполняет маршрутизацию по типу с необязательными защитными условиями
  • Запечатанные классы и исчерпывающее выражение выбора устраняют необходимость в ветке по умолчанию

Часто задаваемые вопросы

Урок «Оператор instanceof» бесплатный?

Да — полный текст урока «Оператор instanceof» бесплатно доступен здесь в веб-версии. Чтобы практиковать его интерактивно (встроенный редактор кода и ИИ-репетитор 24/7) и разблокировать остальной курс Java Academy, подпишись на CoddyKit PRO. Курс Java Academy содержит 4 уроков всего.

Чему я научусь в уроке «Оператор instanceof»?

Используйте instanceof, чтобы проверить типы объектов перед приведением и избежать ClassCastException. Ты практикуешь Java Academy с помощью реального кода, который запускаешь прямо в браузере, и ИИ-репетитор 24/7 отвечает на твои вопросы во время урока.

Нужен ли мне опыт, чтобы начать Java Academy?

Предыдущий опыт не требуется. Java Academy на CoddyKit структурирован для всех уровней — от новичков до продвинутых, поэтому ты можешь начать отсюда или с самого начала и учиться в своем темпе. Это урок 3 из 4.

Сколько времени занимает урок «Оператор instanceof»?

Большинство уроков CoddyKit занимают около 5–10 минут. Каждый из них компактный и интерактивный, поэтому ты постоянно делаешь прогресс и продолжаешь с того же места в веб-версии и приложении.

Можно ли писать и запускать код в этом уроке Java Academy?

Да. Каждый урок Java Academy включает встроенный редактор кода, поэтому ты пишешь и запускаешь реальный код прямо в браузере и получаешь моментальную обратную связь от AI — локальная установка не требуется.

Все уроки этого курса

  1. Примитивные и ссылочные типы
  2. Расширяющие и сужающие преобразования
  3. Оператор instanceof
  4. Приведение типов на практике
← Назад к Java Academy