20. Отфильтровать список пользователей in-place
Условие задачи:
Дан изменяемый список ArrayList<User>.
Необходимо реализовать метод filterUsers(), который изменяет исходный список in-place, оставляя только пользователей, у которых:
имя начинается с
namePrefix;возраст строго больше
18.
Создавать новый список не требуется.
Код:
@Data
class User {
private String name;
private int age;
}
public class UserUtils {
public static void filterUsers(
ArrayList<User> users,
String namePrefix
) {
// ваш код
}
}
Спойлеры к решению
Подсказки
removeIf().💡 Удалять нужно пользователей, которые не удовлетворяют хотя бы одному из условий.
💡 Для проверки имени используй
startsWith(namePrefix).💡 Пользователь остаётся только при
age > 18.Решение
Самый простой вариант:
public static void filterUsers(
ArrayList<User> users,
String namePrefix
) {
users.removeIf(user ->
!user.getName().startsWith(namePrefix)
|| user.getAge() <= 18
);
}
Оставить пользователя нужно, если одновременно выполняются два условия:
user.getName().startsWith(namePrefix)
&& user.getAge() > 18
Следовательно, удалить нужно всё, что этому условию не соответствует:
!user.getName().startsWith(namePrefix)
|| user.getAge() <= 18
removeIf() изменяет исходный список, поэтому дополнительная коллекция не создаётся.
Альтернативный вариант через Iterator:
public static void filterUsers(
ArrayList<User> users,
String namePrefix
) {
Iterator<User> iterator = users.iterator();
while (iterator.hasNext()) {
User user = iterator.next();
if (!user.getName().startsWith(namePrefix)
|| user.getAge() <= 18) {
iterator.remove();
}
}
}
Для ArrayList предпочтительнее removeIf(): он не только короче, но и позволяет удалить подходящие элементы более эффективно, чем последовательные Iterator.remove(), которые могут многократно сдвигать элементы массива.