意外的String.join()行为

时间:2019-02-26 11:42:56

标签: java java-8

我尝试打印List<String>的内容,并在它们之间插入“ ”。紧随Venkat Subramaniam撰写的《 Java函数编程》一书,在第 54 页,他完全按照我的意思做,但是我的打印结果是一个没有逗号的单字符串(,)

String[][] deepArrayStr = new String[][]{{"Alex", "nullpointer"}, {"Eran", "George"}};
 List<String> str= Arrays.stream(deepArrayStr)
     .flatMap(Arrays::stream)
     .collect(Collectors.toList());
for(String s:str){
    System.out.print(String.join(",",s));
}

输出AlexnullpointerEranGeorge

期望Alex,nullpointer,Eran,George


我尝试了另一种方法,但效果很好,我只是想知道在上述方法中我做错了什么,而在《 Venkat》这本书中,我也做过同样的事情?

 System.out.println(Arrays.stream(deepArrayStr)
        .flatMap(Arrays::stream)
        .collect(Collectors.joining(",")));

输出Alex,nullpointer,Eran,George

期望Alex,nullpointer,Eran,George

我的问题不是要从List转换为string,而是要在打印时添加定界符。

3 个答案:

答案 0 :(得分:23)

您要遍历该列表,并每次只用一个条目调用String.join。那永远不会使用定界符。

为清楚起见,请考虑以下两个示例:

String x1 = String.join(",", "a");
String x2 = String.join(",", "a", "b");

然后x1的值将为“ a”,而x2的值将为“ a,b”。 String.join仅在项目之间添加定界符 -因此,如果仅将单个项目传递给定界符,则无需添加任何定界符。

您只需删除for循环,然后将其替换为:

System.out.println(String.join(",", str));

答案 1 :(得分:11)

System.out.print(String.join(",",s));

您正在向每个String调用传递一个String.join,因此当然不会添加任何定界符。如果您传递多个String,则只会添加定界符(在您的情况下为逗号)。

例如,如果您将Stream而不是String收集到List数组中,则可以将该数组传递给String.join

String[] str = Arrays.stream(deepArrayStr)
                     .flatMap(Arrays::stream)
                     .toArray(String[]::new);
System.out.println (String.join (",", str));

这将输出:

Alex,nullpointer,Eran,George

答案 2 :(得分:5)

尽管答案已经突出了差异和可能的解决方法,但这只是为了使其在比较中更具功能性:

您的第一段代码可以转换为:

Arrays.stream(deepArrayStr)
        .flatMap(Arrays::stream)
        .map(s -> String.join(",", s)) //map each string 'if possible' joined by delimeter ,
        .forEach(System.out::print); //print the above mapped string

而另一方面,后者只是这样做:

System.out.println(Arrays.stream(deepArrayStr)
    .flatMap(Arrays::stream)
    .collect(Collectors.joining(","))); //join strings and collect to print (after that)

参考String.join及其相关实现以及Collectors.joining及其功能。