Заполните Arraylist в декларативном стиле Java8 вместо того, чтобы делать это итеративно - PullRequest
0 голосов
/ 25 марта 2020

Можно ли написать следующий код, используя stream и map?

public List<Cake> getChocolateAmmountPerCakeHelperMethod(List<BigDecimal> chocolateAmounts) {
    List<Cake> cakes = new ArrayList<>();
    chocolateAmounts.forEach(chocolateAmount -> {
        Cake cake = new Cake();
        cake.setChocolateAmount(chocolateAmount);
        cakes.add(cake);
    });
    return cakes;
}

Ответы [ 4 ]

3 голосов
/ 25 марта 2020

Ответ Андроника является правильным и наилучшим, когда это применимо, но если вы не можете или не хотите изменять существующие классы, вы можете добиться этого следующим образом:

public List<Cake> getChocolateAmmountPerCakeHelperMethod(List<BigDecimal> chocolateAmounts) {
    return chocolateAmounts.stream()
        .map(anAmount -> {
            Cake cake = new Cake();
            cake.setChocolateAmount(anAmount);
            return cake;
        }).collect(Collectors.toList());
}

Это позволяет вам отображать над каждым элементом в списке с блоком кода, затем соберите сопоставленные результаты в новый список.

1 голос
/ 25 марта 2020

Вы можете создать конструктор для Cake, который принимает chocolateAmount в качестве параметра типа BigDecimal. Затем вы можете использовать map следующим образом:

return chocolateAmounts.stream()
    .map(Cake::new) // here 
    .collect(Collectors.toList());

PS: Ответ предполагает, что вы можете изменить код Cake.

0 голосов
/ 26 марта 2020

В качестве дополнения к Правильный ответ Андроника :

Если вы не можете создать конструктор, потому что не можете изменять источники, вы можете добавить вспомогательный метод:

static Cake createCakeForChocolateAmount(BigDecimal amount){
    Cake cake = new Cake();
    cake.setChocolateAmount(anAmount);
    return cake;
}

Это изменит его код на это:

return chocolateAmounts.stream()
    .map(ThisClass::createCakeForChocolateAmount)
    .collect(Collectors.toList());
0 голосов
/ 25 марта 2020

Вот полностью рабочий пример. Если вам нужен только основной фрагмент кода, то go здесь .

В основном методе я использовал IntStream и преобразовал их в список BigDecimal, который будет используется как количество шоколада.

В getChocolateAmmountPerCakeHelperMethod я создаю список объектов Cake из количества шоколада. Это делается путем потоковой передачи количества шоколада, отображения, т.е. преобразования каждого количества в объект Cake с правильным количеством шоколада, а затем сбора всех Cakes в список. Кроме того, я печатаю все объекты Cake.

import java.math.BigDecimal;
import java.util.List;
import java.util.stream.Collectors;
import java.util.stream.IntStream;

public class CakeMaker {
    public List<Cake> getChocolateAmmountPerCakeHelperMethod(List<BigDecimal> chocolateAmounts) {
        List<Cake> cakes = chocolateAmounts
                .stream()
                //If we had constructor Cake(BigDecimal choco), then map(...) code would be Cake::new OR choco -> new Cake(choco)
                .map(choco -> { Cake cake = new Cake(); cake.setChocolateAmount(choco); return cake;} )
                .collect(Collectors.toList());
        return cakes;
    }

    public static void main(String [] args){
        List<BigDecimal> chocos = IntStream
                .rangeClosed(5, 10)
                .mapToObj( i -> BigDecimal.valueOf(i) )
                .collect(Collectors.toList());

        CakeMaker cm = new CakeMaker();
        List<Cake> cakes = cm.getChocolateAmmountPerCakeHelperMethod(chocos);
        cakes.forEach(System.out::println);
    }
}

Обновлен код класса Cake:

import java.math.BigDecimal;

public class Cake {
    private BigDecimal chocolateAmount;
    public Cake() {}
    public Cake(BigDecimal chocolateAmount) {
        this.chocolateAmount = chocolateAmount;
    }
    public void setChocolateAmount(BigDecimal chocolateAmount) {
        this.chocolateAmount = chocolateAmount;
    }
    @Override
    public String toString(){
        return "CAKE [ choco = " + chocolateAmount + "]";
    }
}

Вывод:

CAKE [ choco = 5]
CAKE [ choco = 6]
CAKE [ choco = 7]
CAKE [ choco = 8]
CAKE [ choco = 9]
CAKE [ choco = 10]
...