Home > Net >  Java Stream usage
Java Stream usage

Time:09-10

I have a usecase where I want to modify some entries in a list based on some condition and leave the rest as it is. For this I am thinking of using java streams but I could not find a solution that will work. I know using filter and map won't work as it will filter out the elements which do not satisfy the condition. Is there something that I can use?

Example -

List<Integer> a = new ArrayList<>();
a.add(1); a.add(2);

// I want to get square of element if element is even 
// Current solution 
List<Integer> b = a.stream().filter(i -> i % 2 == 0).map(i -> i * i).collect(Collectors.toList());

// This outputs - b = [4]
// But I want - b = [1, 4]

CodePudding user response:

You can make the map operation conditional and remove the filter:

List<Integer> b = a.stream()
            .map(i -> i % 2 == 0 ? i * i : i)
            .collect(Collectors.toList());

CodePudding user response:

You don't realy need streams and create a new list if all you want is modify some entries. Instead you can use List#replaceAll

a.replaceAll(i -> i % 2 == 0 ? i * i : i);

CodePudding user response:

You can just put the condition in the map like this:

List<Integer> a = new ArrayList<>();
a.add(1);
a.add(2);
List<Integer> b = a.stream().map(i -> i % 2 == 0 ? i * i : i).collect(Collectors.toList());

CodePudding user response:

Unfortunately a List<FooData> may alter FooData fields, but a List<Integer> is a bit harder;

List<FooData> list = ...;
list.stream()
    .filter(fd -> fd.deservesMore())
    .filter(fd::deservesMore)
    .forEach(fd -> fd.setSalary(fd.getSalary()**2);

For a List<Integer> I hesitate, I saw an answer with a map to a conditional change. Either the integer is part of a more complex object, or it could be held in an array, where the index has some meaning.

int[] a = {1, 2};
IntStream.ofRange(0, a.length)
    .filter(i -> i % 2 == 0)
    .forEach(i -> a[i] *= a[i]);

This is nothing but a _for-i_loop.

I think you wanted something like:

List<AtomicInteger> a = new ArrayList<>();
Collection.addAll(a,
    new AtomicInteger(1),
    new AtomicInteger(2));
a.stream()
    .filter(i -> i.get() % 2 == 0)
    .forEach(i -> i.set(i.get() * i.get()));
  • Related