如何加入列表项,但为最后一项使用不同的分隔符?

Xor*_*rty 7 java

给出如下列表:

List<String> names = Lists.newArrayList("George", "John", "Paul", "Ringo")

我想将它转换为这样的字符串:

George, John, Paul and Ringo

我可以用相当笨拙的StringBuilder事情做到这一点:

String nameList = names.stream().collect(joining(", "));
        if (nameList.contains(",")) {
            StringBuilder builder = new StringBuilder(nameList);
            builder.replace(nameList.lastIndexOf(','), nameList.lastIndexOf(',') + 1, " and");
            return builder.toString();
        }
Run Code Online (Sandbox Code Playgroud)

是否有更优雅的方法?如果需要,我不介意使用库.

注意:

  • 我可以使用for带索引的旧循环,但我不是在寻找这样的解决方案
  • 值(名称)中没有逗号

swi*_*ler 2

正如您已经完成的大部分操作一样,我将介绍第二种方法“replaceLast”,到目前为止,该方法不在 java.lang.String 的 JDK 中:

import java.util.List;
import java.util.stream.Collectors;

public final class StringUtils {
 private static final String AND = " and ";
 private static final String COMMA = ", ";

 // your initial call wrapped with a replaceLast call
 public static String asLiteralNumeration(List<String> strings) {
    return replaceLast(strings.stream().collect(Collectors.joining(COMMA)), COMMA, AND);
 }

 public static String replaceLast(String text, String regex, String replacement) {
    return text.replaceFirst("(?s)" + regex + "(?!.*?" + regex + ")", replacement);
 }
}
Run Code Online (Sandbox Code Playgroud)

您也可以更改分隔符和参数。到目前为止,这里是您的要求的测试:

@org.junit.Test
public void test() {
 List<String> names = Arrays.asList("George", "John", "Paul", "Ringo");
 assertEquals("George, John, Paul and Ringo", StringUtils.asLiteralNumeration(names));

 List<String> oneItemList = Arrays.asList("Paul");
 assertEquals("Paul", StringUtils.asLiteralNumeration(oneItemList));

 List<String> emptyList = Arrays.asList("");
 assertEquals("", StringUtils.asLiteralNumeration(emptyList));

}
Run Code Online (Sandbox Code Playgroud)