如何将Java中的范围(使用java.util.stream.LongStream
或java.util.stream.IntStream
)转换为Java中的分隔字符串?
我试过了:
String str = LongStream.range(16, 30)
.boxed()
.map(String::valueOf)
.collect(Collectors.joining(","));
System.out.println(str);
打印:
16,17,18,19,20,21,22,23,24,25,26,27,28,29
同样可以与IntStream
一起使用。是否有更方便的范围转换为分隔字符串?
答案 0 :(得分:7)
说真的,只是为了它的乐趣。使用番石榴:
String result = ContiguousSet.create(
Range.closedOpen(16, 31), DiscreteDomain.integers())
.asList()
.toString();
或者
String result = String.join(",",
IntStream.rangeClosed(16, 30).mapToObj(String::valueOf).toArray(String[]::new));
或者:
String result = String.join(",",
() -> IntStream.rangeClosed(16, 31).mapToObj(x -> (CharSequence) String.valueOf(x)).iterator());
或(好像我对此有所了解):
String result = IntStream.rangeClosed(16, 31)
.boxed()
.collect(
Collector.of(
() -> new Object() {
StringBuilder sb = new StringBuilder();
},
(obj, i) -> obj.sb.append(i).append(",")
,
(left, right) -> {
left.sb.append(right.sb.toString());
return left;
},
x -> {
x.sb.setLength(x.sb.length() - 1);
return x.sb.toString();
})
);
在Holger的优点之后,这里的版本更简单:
StringBuilder sb = IntStream.range(16, 30)
.collect(
StringBuilder::new,
(builder, i) -> builder.append(i).append(", "),
StringBuilder::append);
if (sb.length() != 0) {
sb.setLength(sb.length() - 2);
}
String result = sb.toString();
答案 1 :(得分:6)
String s = IntStream.range(16, 30)
.mapToObj(String::valueOf)
.collect(Collectors.joining(","));
答案 2 :(得分:0)
如果您的方便感意味着代码较少,则无需明确将Long
映射到String
。可以在收集过程时简单地映射它们。这是代码:
List<String> str = LongStream.range(16, 30)
.boxed()
.collect(Collectors.mapping(l -> String.valueOf(l), Collectors.toList()));
System.out.println(str.toString());
结果是:
[16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29]
回应关于是否应该避免boxing
的评论,无论如何都必须发生。在这种情况下,range()
会返回LongStream
的对象,该对象必须转换为stream
Long
。
根据@Jubobs,mapToObject()
有效地从stream
对象返回Long
LongStream
。