Java 8从列表中删除大小写无关的重复字符串

时间:2018-07-27 07:12:00

标签: java java-8

如何在不考虑每个单词的大小写的情况下从字符串列表中删除重复的元素,例如考虑以下代码片段

    String str = "Kobe Is is The the best player In in Basketball basketball game .";
    List<String> list = Arrays.asList(str.split("\\s"));
    list.stream().distinct().forEach(s -> System.out.print(s+" "));

这仍然提供与下面相同的输出,这很明显

Kobe Is is The the best player In in Basketball basketball game .

我需要如下结果

Kobe Is The best player In Basketball game .

8 个答案:

答案 0 :(得分:6)

从字面上回答您的问题,“无论列表中是否有大小写,都删除重复的字符串”,您可以使用

// just for constructing a sample list
String str = "Kobe Is is The the best player In in Basketball basketball game .";
List<String> list = new ArrayList<>(Arrays.asList(str.split("\\s")));

// the actual operation
TreeSet<String> seen = new TreeSet<>(String.CASE_INSENSITIVE_ORDER);
list.removeIf(s -> !seen.add(s));

// just for debugging
System.out.println(String.join(" ", list));

答案 1 :(得分:3)

如果只需要除去连续的重复项,则可以使用正则表达式。下面的正则表达式会检查重复的单词,忽略大小写。

String input = "Kobe Is is The the best player In in Basketball basketball game .";
String output = input.replaceAll("(?i)\\b(\\w+)\\s+\\1\\b", "$1");

System.out.println(output);

哪个输出:

Kobe Is The best player In Basketball game .

答案 2 :(得分:3)

这是一个有趣的解决方案,可以通过使用流来获得预期的结果。

String result = Pattern.compile("\\s")
                .splitAsStream(str)
                .collect(Collectors.collectingAndThen(Collectors.toMap(String::toLowerCase,
                        Function.identity(),
                        (l, r) -> l,
                        LinkedHashMap::new),
                        m -> String.join(" ", m.values())));

打印:

Kobe Is The best player In Basketball game .

答案 3 :(得分:0)

如果在打印所有大写字母时输掉不是问题,您可以采用这种方式

    list.stream()
            .map(String::toLowerCase)
            .distinct()
            .forEach(System.out::print)

输出:

  

科比是篮球比赛中最好的球员。

答案 4 :(得分:0)

保留大写字母并删除小写字母:

String str = "Kobe Is is The the best player In in Basketball basketball game .";
List<String> list = Arrays.asList(str.split("\\s"));
for(int i = 1; i<list.size(); i++)
{
        if(list.get(i).equalsIgnoreCase(list.get(i-1)))
        {
            // is lower case
            if(list.get(i).toLowerCase().equals(list.get(i)))
            {
                list.set(i,"");
            }
            else
            {
                list.set(i-1, "");
            }
        }
}

list.stream().distinct().forEach(s -> System.out.print(s+" "));             

答案 5 :(得分:0)

这是一个单行解决方案:

此解决方案利用jOOλ库及其Seq.distinct(Function<T,U>)方法:

List<String> distinctWords = Seq.seq(list).distinct(String::toLowerCase).toList();

结果(当打印成问题时):

  

神户是篮球比赛中最好的球员。

答案 6 :(得分:0)

重复字符串的问题是,在完全相同的情况下,这些单词不会出现,第一个单词是Basketball,另一个单词是basketball,因此这两个单词不是相同的。首字母B出现在这里。因此,您可以做的是将字符串进行小写或大写的比较,也可以忽略大小写进行比较。

答案 7 :(得分:0)

TreeSet提供的解决方案非常优雅。但是TreeSet还会对使解决方案效率低下的元素进行排序。 下面的代码演示了如何使用HashMap来更有效地实现它,该方法优先考虑具有大写字母的字符串

class SetWithIgnoreCase {
    private HashMap<String, String> underlyingMap = new HashMap<>();

    public void put(String str) {
        String lowerCaseStr = str.toLowerCase();
        underlyingMap.compute(lowerCaseStr, (k, v) -> (v == null) ? str : (compare(v, str) > 0 ? v : str));
    }

    private int compare(String str1, String str2) {
        int upperCaseCnt1 = 0;
        int upperCaseCnt2 = 0;
        for (int i = 0; i < str1.length(); i++) {
            upperCaseCnt1 += (Character.isUpperCase(str1.charAt(i)) ? 1 : 0);
            upperCaseCnt2 += (Character.isUpperCase(str2.charAt(i)) ? 1 : 0);
        }
        return upperCaseCnt1 - upperCaseCnt2;
    }
}