1. Обзор
Java предоставляет множество методов и классов для объединения String
s .
Однако результирующая строка
может содержать некоторые нежелательные значения, если мы не будем обращать внимание на нулевые
объекты.
В этом руководстве мы рассмотрим некоторые подходы, позволяющие избежать нулевых
объектов String при объединении
String
s.
2. Постановка задачи
Допустим, мы хотим объединить элементы массива String
, где любой из элементов может быть нулевым
.
Мы можем просто сделать это с помощью оператора +:
String[] values = { "Java ", null, "", "is ", "great!" };
String result = "";
for (String value : values) {
result = result + value;
}
Это объединит все элементы в результирующую строку
, как показано ниже:
Java nullis great!
Но мы можем не захотеть отображать или добавлять такие «нулевые» значения к выводу.
Точно так же мы получаем тот же вывод, используя статический метод String.join()
, если наше приложение работает на Java 8 или более поздней версии:
String result = String.join("", values);
Мы также не можем избежать объединения нулевых элементов при использовании метода String.join()
.
Давайте рассмотрим некоторые подходы, позволяющие избежать конкатенации нулевых
элементов и получить ожидаемый результат: «Java великолепна!».
3. Использование оператора +
Оператор сложения (+) перегружен для объединения строк
в Java. При объединении с помощью оператора + мы можем проверить, является ли строка нулевой
,
и заменить нулевую
строку
пустой («») строкой:
for (String value : values) {
result = result + (value == null ? "" : value);
}
assertEquals("Java is great!", result);
В качестве альтернативы мы можем извлечь код, проверяющий String на
null
, во вспомогательный метод, который принимает объект String
и возвращает объект String , отличный от
null
:
for (String value : values) {
result = result + getNonNullString(value);
}
Здесь метод getNonNullString()
является нашим вспомогательным методом. Он просто проверяет нулевую
ссылку входного объекта String .
Если входной объект равен null
, он возвращает пустую («») String
, в противном случае он возвращает ту же String
:
return value == null ? "" : value;
Однако, как мы знаем, объекты String неизменяемы в Java.
Это означает, что каждый раз, когда мы объединяем объекты String
с помощью оператора +, в памяти создается новая строка .
Таким образом, использование оператора + для конкатенации оказывается дорогостоящим .
Кроме того, мы можем использовать этот подход для создания вспомогательного метода для проверки объектов null
String
в различных других операциях, поддерживающих конкатенацию. Давайте посмотрим на некоторые из них.
4. Использование метода String.concat()
Метод String.conca
t
()
`` — хороший выбор, когда мы хотим объединить объекты
String .
Здесь мы можем использовать наш метод getNonNullString()
, который проверяет нулевой
объект и возвращает пустую строку
:
for (String value : values) {
result = result.concat(getNonNullString(value));
}
Пустая строка
, возвращаемая методом getNonNullString()
, объединяется с результатом, игнорируя, таким образом, нулевые
объекты.
5. Использование класса StringBuilder
StringBuilder
предоставляет множество полезных и удобных методов построения строк .
Одним из них является метод append()
.
Здесь мы также можем использовать тот же метод getNonNullString()
, чтобы избежать нулевых
объектов при использовании метода append()
:
for (String value : values) {
result = result.append(getNonNullString(value));
}
6. Использование класса StringJoiner
(Java 8+)
Класс StringJoiner
предоставляет все функции String.join()
, а также возможность начинать с заданного префикса и заканчивать заданным суффиксом .
Мы можем использовать его метод add() для конкатенации
String
s.
Как и прежде, мы можем использовать наш вспомогательный метод getNonNullString()
, чтобы избежать конкатенации нулевых
значений String :
StringJoiner result = new StringJoiner("");
for (String value : values) {
result = result.add(getNonNullString(value));
}
Одно из различий между String.join()
и StringJoiner
заключается в том, что в отличие от String.join()
, мы должны перебрать коллекцию ( массив, список и
т. д .), чтобы соединить все элементы.
7. Использование Streams.filter
(Java 8+)
Stream
API предоставляет значительное количество последовательных и параллельных агрегатных операций. Одной из таких операций с промежуточным потоком является фильтрация
, которая принимает Предикат
в качестве входных данных и преобразует Поток
в другой Поток
на основе данного Предиката.
Итак, мы можем определить предикат
, который будет проверять нулевое
значение строки
и передавать этот предикат
в метод filter()
. Следовательно, фильтр
будет отфильтровывать эти нулевые
значения из исходного потока.
В конце концов, мы можем объединить все эти ненулевые строковые
значения
с помощью Collectors.joining()
и, наконец, собрать результирующий поток
в строковую
переменную:
result = Stream.of(values).filter(value -> null != value).collect(Collectors.joining(""));
8. Заключение
В этой статье мы проиллюстрировали различные подходы, позволяющие избежать конкатенации нулевых
объектов String .
Всегда будет более одного правильного подхода к удовлетворению наших требований. Итак, мы должны определить, какой подход лучше всего подходит для данного места.
Мы должны помнить, что объединение самой строки
может быть дорогостоящей операцией, особенно в циклах. Таким образом, всегда рекомендуется принимать во внимание аспекты производительности Java String
API.
Как всегда, код этих примеров доступен на GitHub .