Вы можете добавить второй компаратор для определения порядка после сравнения их без учета регистра.Второй компаратор размещается на основе символов.
List<String> l = Arrays.asList("a","A","A","a","B","c","C");
l.sort(String.CASE_INSENSITIVE_ORDER
.thenComparing(Comparator.comparing(YourClass::isUpperCase)
.reversed()));
private static boolean isUpperCase(String s) {
return Character.isUpperCase(s.charAt(0));
}
Comparator.comparing
использует вспомогательный метод для определения, является ли строка заглавной.Тип возврата этого метода - логический .Естественное упорядочение логического типа: false , за которым следует true .Следовательно, вы должны повернуть его вспять, чтобы сначала получить символы (строки) в верхнем регистре.
Примечание: Вы должны были использовать здесь символы, а не строки (если все строки имеют только однуперсонаж).Вспомогательный метод здесь просто проверяет первый символ в этой строке, который звучит странно!.
В качестве альтернативы, если у вас есть метод проверки нижнего регистра, вы можете упростить это как
l.sort(String.CASE_INSENSITIVE_ORDER
.thenComparing(YourClass::isLowerCase));
private static boolean isLowerCase(String s) {
return Character.isLowerCase(s.charAt(0));
}
ОБНОВЛЕНИЕ: (согласно обновлению ОП вопроса).
Если строка состоит из нескольких символов и если вы хотите сделать заказ, исходя из условия, что строки в верхнем регистре должны предшествовать первымдругие, вы можете сделать, как.
l.sort(String.CASE_INSENSITIVE_ORDER
.thenComparing(YourClass::areAllCharactersLowerCase));
private static boolean areAllCharactersLowerCase(String s) {
return s.chars()
.mapToObj(c -> (char)c)
.allMatch(Character::isLowerCase);
}
Примечание: При этом строки типа CCc
и Ccc
будут обрабатываться равными в соответствии с первым компаратором, а второй компаратор вернет false для обоих (обработка их)снова равный).Таким образом, они отображаются в том же порядке, что и во входных данных.
РЕДАКТИРОВАТЬ 2: На основе комментария OP
Что если он имеетСтроки, такие как ААа или ААА или ААА?
@ user7, тогда AAa, AaA, aAA должны быть в порядке.
Я предполагаю, что вы хотите упорядочить строки, сравнивая символ за символом, и строка с наиболее последовательным символом в верхнем регистре будет считаться перечисленной перед другими.
Приведенный ниже код сравнивает char-by-char и обрабатывает следующие сценарии
- Если текущий символ String
a
имеет верхний регистр, а текущий символ String b
в нижнем регистре, тогда String a
предшествует b
. - Если текущий символ String
a
имеет нижний регистр, а текущий символ String b
в верхнем регистре,затем String b
предшествует a
- Иначе, оба имеют одинаковый символ. Продолжайте поиск.
Для одинаковых строк мы возвращаем 0 в конце.
l.sort(String.CASE_INSENSITIVE_ORDER
.thenComparing((a, b) -> {
//String a and b are equal when compared ignoring case (and hence same length)
for (int i = 0; i < a.length(); i++) {
if (Character.isUpperCase(a.charAt(i)) && Character.isLowerCase(b.charAt(i))) {
return -1;
} else if (Character.isLowerCase(a.charAt(i)) && Character.isUpperCase(b.charAt(i))) {
return 1;
}
}
return 0;
}));