Ссылки на статические методы
Заменяйте лямбда-выражения, вызывающие статические методы, ссылками ClassName::methodName.
«Ссылки на статические методы» — бесплатный урок Java Academy на CoddyKit. Это урок 1 из 4. Ты можешь прочитать весь урок бесплатно ниже — а потом практиковать его прямо в браузере с встроенным редактором кода и ИИ-репетитором 24/7. Это часть пути обучения Java Academy, и твой прогресс синхронизируется между веб-версией и приложением CoddyKit. Курс Java Academy содержит 4 уроков всего.
Что такое ссылки на методы?
Ссылка на метод — это сокращённая форма лямбда-выражения, делегирующая вызов существующему методу. Если лямбда просто вызывает один метод, ссылка на метод делает код более кратким и понятным.
import java.util.*;
import java.util.stream.*;
List<String> names = List.of("Alice", "Bob", "Carol");
// Lambda:
names.forEach(s -> System.out.println(s));
// Equivalent method reference:
names.forEach(System.out::println);Синтаксис ссылки на статический метод
Ссылка на статический метод имеет форму ClassName::staticMethodName. Её можно использовать везде, где функциональный интерфейс ожидает метод с такой же сигнатурой.
import java.util.stream.*;
// Integer.parseInt(String) matches Function<String, Integer>
List<String> strs = List.of("1","2","3","4","5");
List<Integer> nums = strs.stream()
.map(Integer::parseInt) // replaces s -> Integer.parseInt(s)
.collect(Collectors.toList());
System.out.println(nums); // [1, 2, 3, 4, 5]Math.abs как ссылка на метод
На статические методы вспомогательных классов, таких как Math, можно ссылаться напрямую:
import java.util.*;
import java.util.stream.*;
List<Integer> values = List.of(-3, 5, -1, 8, -4);
List<Integer> abs = values.stream()
.map(Math::abs) // replaces v -> Math.abs(v)
.collect(Collectors.toList());
System.out.println(abs); // [3, 5, 1, 8, 4]Ссылка на статический метод с Predicate
Статические методы, возвращающие логическое значение, могут использоваться как Predicate:
import java.util.stream.*;
// String.isEmpty() is an instance method, but we can use a static helper
// Objects.isNull matches Predicate<Object>
List<String> mixed = Arrays.asList("hello", null, "world", null);
long nullCount = mixed.stream()
.filter(Objects::isNull)
.count();
System.out.println(nullCount); // 2
long nonNull = mixed.stream()
.filter(Objects::nonNull)
.count();
System.out.println(nonNull); // 2Статическая ссылка Comparator
На статические методы, соответствующие Comparator, также можно ссылаться напрямую:
import java.util.*;
import java.util.stream.*;
List<String> words = List.of("banana", "apple", "cherry");
// String.CASE_INSENSITIVE_ORDER is a Comparator
List<String> sorted = words.stream()
.sorted(String::compareToIgnoreCase)
.collect(Collectors.toList());
System.out.println(sorted); // [apple, banana, cherry]Пользовательский статический вспомогательный метод
Определите статический вспомогательный метод и ссылайтесь на него напрямую:
class Validator {
static boolean isPositive(int n) { return n > 0; }
static String toLabel(int n) { return n > 0 ? "POS" : "NEG"; }
}
List<Integer> nums = List.of(-2, 3, -1, 5, 0);
List<Integer> positive = nums.stream()
.filter(Validator::isPositive)
.collect(Collectors.toList());
System.out.println(positive); // [3, 5]
List<String> labels = nums.stream()
.map(Validator::toLabel)
.collect(Collectors.toList());BiFunction со статическим методом
Статические методы, принимающие два параметра, могут соответствовать BiFunction<T,U,R>:
import java.util.function.*;
// Math.max(int,int) → BiFunction... but needs IntBinaryOperator
java.util.function.IntBinaryOperator maxOp = Math::max;
System.out.println(maxOp.applyAsInt(7, 3)); // 7
// String.format as BiFunction? Only works if signature matches:
// Integer.sum(int,int) → IntBinaryOperator
java.util.function.IntBinaryOperator sum = Integer::sum;
System.out.println(sum.applyAsInt(10, 20)); // 30Сортировка с Comparator.comparing и статической ссылкой
Объединяйте Comparator.comparing со ссылками на методы для удобной сортировки:
record Person(String name, int age) {}
List<Person> people = List.of(
new Person("Charlie",30), new Person("Alice",25), new Person("Bob",35)
);
people.stream()
.sorted(Comparator.comparing(Person::name))
.forEach(p -> System.out.println(p.name()));
// Alice, Bob, CharlieКогда использовать ссылки на статические методы
Используйте ссылки на статические методы, когда:
- Тело лямбды представляет собой единственный вызов статического метода
- Преобразовывать аргументы не требуется
- Сигнатура метода соответствует функциональному интерфейсу
Если нужно преобразовать аргументы или добавить логику, используйте лямбду.
Сравнение читаемости
Сравнение стилей лямбды и ссылки на метод рядом:
// Lambda style
Stream.of("1","2","3").map(s -> Integer.parseInt(s));
Stream.of(1,-2,3).filter(n -> n > 0);
Stream.of(-5,2,-1).map(n -> Math.abs(n));
// Method reference style
Stream.of("1","2","3").map(Integer::parseInt);
Stream.of(1,-2,3).filter(Validator::isPositive);
Stream.of(-5,2,-1).map(Math::abs);Распространённая ошибка: неверная сигнатура
Ссылка на метод работает только тогда, когда её сигнатура точно соответствует абстрактному методу функционального интерфейса. Если типы или количество аргументов различаются, используйте вместо неё обёртку-лямбду.
// Math.pow(double, double) needs two args — can't use as Function<Double, Double>
// This won't compile:
// Function<Double, Double> square = Math::pow; // ERROR
// Fix with lambda:
Function<Double, Double> square = n -> Math.pow(n, 2);
System.out.println(square.apply(5.0)); // 25.0Быстрая проверка
Какой из следующих вариантов является допустимой ссылкой на статический метод, работающей как Predicate<Object>?
Повторение: ссылки на статические методы
Основные выводы:
- Синтаксис: ClassName::staticMethodName
- Заменяет лямбды, делегирующие вызов одному статическому методу
- Сигнатура метода должна соответствовать абстрактному методу функционального интерфейса
- Работает с Predicate, Function, Consumer, Comparator и другими интерфейсами
- Используйте лямбды, если требуется преобразование аргументов или дополнительная логика
Часто задаваемые вопросы
Урок «Ссылки на статические методы» бесплатный?
Да — полный текст урока «Ссылки на статические методы» бесплатно доступен здесь в веб-версии. Чтобы практиковать его интерактивно (встроенный редактор кода и ИИ-репетитор 24/7) и разблокировать остальной курс Java Academy, подпишись на CoddyKit PRO. Курс Java Academy содержит 4 уроков всего.
Чему я научусь в уроке «Ссылки на статические методы»?
Заменяйте лямбда-выражения, вызывающие статические методы, ссылками ClassName::methodName. Ты практикуешь Java Academy с помощью реального кода, который запускаешь прямо в браузере, и ИИ-репетитор 24/7 отвечает на твои вопросы во время урока.
Нужен ли мне опыт, чтобы начать Java Academy?
Предыдущий опыт не требуется. Java Academy на CoddyKit структурирован для всех уровней — от новичков до продвинутых, поэтому ты можешь начать отсюда или с самого начала и учиться в своем темпе. Это урок 1 из 4.
Сколько времени занимает урок «Ссылки на статические методы»?
Большинство уроков CoddyKit занимают около 5–10 минут. Каждый из них компактный и интерактивный, поэтому ты постоянно делаешь прогресс и продолжаешь с того же места в веб-версии и приложении.
Можно ли писать и запускать код в этом уроке Java Academy?
Да. Каждый урок Java Academy включает встроенный редактор кода, поэтому ты пишешь и запускаешь реальный код прямо в браузере и получаешь моментальную обратную связь от AI — локальная установка не требуется.
Все уроки этого курса
- Ссылки на статические методы
- Ссылки на методы экземпляра конкретного объекта
- Ссылки на методы произвольного экземпляра
- Ссылки на конструкторы