Importante

Você está vendo a versão anterior da nova experiência da Alura que estamos preparando para você. Em breve, ela ganha uma identidade visual novinha totalmente pensada em potencializar seus estudos!

1
resposta

Desafio: hora da prática

**Exercício 1: **

package streams;

import java.util.Arrays;
import java.util.IntSummaryStatistics;
import java.util.List;

public class SummaryStatistics {
    public static void main(String[] args) {
        List<Integer> numeros = Arrays.asList(10, 20, 30, 40, 50);
        IntSummaryStatistics numeroStatistics = numeros.stream()
                .mapToInt(Integer::intValue)
                        .summaryStatistics();


        System.out.println("Maior número da lista é: " +  numeroStatistics.getMax());

    }
}

**Exercício 2: **

package streams;

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

public class GroupingByLength {
    public static void main(String[] args) {
        List<String> palavras = Arrays.asList("java", "stream", "lambda", "code");

        Map<Integer, List<String>> palavrasPorTamanho = palavras.stream()
                .collect(Collectors.groupingBy(String::length));

        System.out.println(palavrasPorTamanho);
    }
}

**Exercício 3: **

package streams;

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

public class Joining {
    public static void main(String[] args) {
        List<String> nomes = Arrays.asList("Alice", "Bob", "Charlie");

        String resultado = nomes.stream()
                .collect(Collectors.joining(", "));
        System.out.println(resultado);
    }
}

**Exercício 4: **

package streams;

import java.util.Arrays;
import java.util.List;

public class Main {
    public static void main(String[] args) {
        List<Integer> numeros = Arrays.asList(1,2,3,4,5,6);

        int numerosParesAoQuadrado = numeros.stream()
                .filter(n -> n % 2 == 0)
                .map(n -> n * n)
                .reduce(0, Integer::sum);

        System.out.println(numerosParesAoQuadrado);
    }
}

**Exercício 5: **

package streams;

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

public class Main {
    public static void main(String[] args) {
        List<Integer> lista = Arrays.asList(1, 2, 3, 4, 5, 6);

        Map<Boolean, List<Integer>> numerosDividos = lista.stream()
                .collect(Collectors.partitioningBy(n -> n % 2 == 0));

        System.out.println("Pares: " + numerosDividos.get(true));
        System.out.println("Ímpares: " + numerosDividos.get(false));
    }
}

**Exercício 6: **

public class Main {
    public static void main(String[] args) {
        List<Produto> produtos = Arrays.asList(
            new Produto("Smartphone", 800.0, "Eletrônicos"),
            new Produto("Notebook", 1500.0, "Eletrônicos"),
            new Produto("Teclado", 200.0, "Eletrônicos"),
            new Produto("Cadeira", 300.0, "Móveis"),
            new Produto("Monitor", 900.0, "Eletrônicos"),
            new Produto("Mesa", 700.0, "Móveis")
        );
Map<String, List<Produto>> produtosCategoria = produtos.stream()
                    .collect(Collectors.groupingBy(Produto::getCategoria));

            produtosCategoria.forEach((nomeCategoria, nomeProdutos) ->
                    System.out.println(nomeCategoria + ": " + nomeProdutos));
        
    }
}

**Exercício 7: **

public class Main {
    public static void main(String[] args) {
        List<Produto> produtos = Arrays.asList(
        ...
        );
         Map<String, Long> quantidadePorCategoria = produtos.stream()
                    .collect(Collectors.groupingBy(Produto::getCategoria, Collectors.counting()));

            System.out.println("Quantidade de produtos: " + quantidadePorCategoria);
        }
    }
        
    }
}

**Exercício 8: **

  Map<String, Optional<Produto>> produtosMaisCaros = produtos.stream()
                    .collect(Collectors.groupingBy(
                            Produto::getCategoria,
                            Collectors.maxBy(
                                    Comparator.comparingDouble(Produto::getPreco)
                            )
                    ));
            System.out.println(produtosMaisCaros);
        
    }
}

**Exercício 9: **

       Map<String, Double> precosCategoria = produtos.stream()
                    .collect(Collectors.groupingBy(
                            Produto::getCategoria,
                                    Collectors.summingDouble(Produto::getPreco)));


            System.out.println(precosCategoria);

        }
    }
1 resposta

Oii, Luan! Como vai?

Parabéns pela resolução da atividade Desafio: hora da prática!

Vi que você explorou a IntSummaryStatistics pra reunir estatísticas de uma lista numérica com Java, utilizou muito bem o Collectors.groupingBy pra agrupar produtos por categoria e ainda compreendeu a importância do Collectors.partitioningBy pra dividir elementos em dois grupos a partir de uma condição booleana.

Uma dica interessante pra o futuro é combinar o Collectors.collectingAndThen com o maxBy, assim o mapa final já entrega o objeto pronto em vez de um Optional. Algo assim:

Map<String, Produto> produtosMaisCaros = produtos.stream()
        .collect(Collectors.groupingBy(
                Produto::getCategoria,
                Collectors.collectingAndThen(
                        Collectors.maxBy(Comparator.comparingDouble(Produto::getPreco)),
                        resultado -> resultado.orElse(null)
                )
        ));

produtosMaisCaros.forEach((categoria, produto) ->
        System.out.println(categoria + ": " + produto));

Isso faz com que a transformação final aconteça dentro do próprio coletor, deixando a leitura do mapa mais direta para quem consome o resultado depois.

Se quiser aprofundar ainda mais, algumas boas práticas são:

  • Streams primitivas: quando o cálculo envolve apenas números, mapToInt, mapToDouble e mapToLong evitam o boxing desnecessário e deixam métodos como sum() e average() disponíveis diretamente.
  • Coletores encadeados: o segundo parâmetro do groupingBy aceita outros coletores, como counting(), summingDouble() e mapping(), o que permite montar relatórios completos em uma única passagem pela stream.
  • Streams não reutilizáveis: cada stream é consumida uma única vez pela operação terminal, então vale sempre partir da coleção original quando precisar de um novo fluxo.

Ah, uma pergunta: O que você achou mais natural de escrever nesses exercícios: as operações intermediárias encadeadas, como filter e map, ou os coletores do Collectors na hora de fechar o fluxo?

Alguns materiais podem estar em inglês, mas é possível compreendê-los usando o recurso de tradução de páginas do próprio navegador.

Alura Conte com o apoio da comunidade Alura na sua jornada. Abraços e bons estudos!