This question
Is there a concise way to iterate over a stream with indices in Java 8?
describes how to drive one stream based on another stream of indexes. My goal is to take an array of strings
one two three four five six seven eight
and all-cap the elements having an array index between 2 and 5:
one two THREE FOUR FIVE SIX seven eight
I've figured out how to do this, but my instinct says there should be a more elegant way of going about it. In the below example, the first stream filters out all elements except those in range. It's not directly what I want, of course, but it's similar in how it uses a stream to filter by index-range. The second alters the array elements in place, capitalizing the ones I want.
I don't like how it alters the array in place, and how it requires two streams. Is there a better way?
import static java.util.stream.Collectors.joining;
import java.util.Arrays;
import java.util.stream.IntStream;
public class UpperCaseElementsInIndexRangeViaIntStream {
public static void main(String[] ignored) {
final String input = "one two three four five six seven eight";
final int MIN_IDX = 2;
final int MAX_IDX = 5;
final String[] splits = input.split(" ");
//Filter only those in range
String output = IntStream.range(0, splits.length).
filter(idx -> MIN_IDX <= idx && idx <= MAX_IDX).
mapToObj(i -> splits[i]).
collect(joining(" "));
System.out.println(output);
//Change the array in place, capitalizing only those in range
IntStream.range(0, splits.length).forEach(idx -> {
final String split = splits[idx];
splits[idx] = (MIN_IDX <= idx && idx <= MAX_IDX)
? split.toUpperCase() : split;
});
output = Arrays.stream(splits).collect(joining(" "));
System.out.println(output);
}
}
Output:
three four five six
one two THREE FOUR FIVE SIX seven eight