Encontrando o valor mais alto em um mapa Java

Encontrando o valor mais alto em um mapa Java

1. Visão geral

Neste tutorial rápido,we’ll explore various ways to find the maximum value in a Java Map. Também veremos como os novos recursos emJava 8 simplificaram essa operação.

Antes de começar, vamos recapitular brevemente comoobjects are compared em Java.

Normalmente, os objetos podem expressar uma ordem natural implementando o métodocompareTo() da interfaceComparable. No entanto, uma ordem diferente da ordem natural pode ser empregada por meio de um objetoComparator. Veremos isso em mais detalhes à medida que prosseguirmos.

2. Antes do Java 8

Vamos começar explorando primeiro como podemos encontrar o valor mais alto sem os recursos do Java 8.

2.1. Usando iteração simples

Usando a iteração, poderíamos simplesmente percorrer todas as entradas de aMap para escolher o valor mais alto, armazenando o mais alto atual em uma variável:

public > V maxUsingIteration(Map map) {
    Map.Entry maxEntry = null;
    for (Map.Entry entry : map.entrySet()) {
        if (maxEntry == null || entry.getValue()
            .compareTo(maxEntry.getValue()) > 0) {
            maxEntry = entry;
        }
    }
    return maxEntry.getValue();
}

Aqui, também estamos fazendo uso de genéricos Java para construir um método que pode ser aplicado a diferentes tipos.

2.2. UsandoCollections.max()

Agora vamos ver como o método utilitáriomax() na classeCollections pode nos salvar de escrever muito disso nós mesmos:

public > V maxUsingCollectionsMax(Map map) {
    Entry maxEntry = Collections.max(map.entrySet(), new Comparator>() {
        public int compare(Entry e1, Entry e2) {
            return e1.getValue()
                .compareTo(e2.getValue());
        }
    });
    return maxEntry.getValue();
}

Neste exemplo,we’re passing a Comparator object to max() que pode alavancar a ordem natural dos valoresEntry por meio decompareTo() ou implementar uma ordem totalmente diferente.

3. Após o Java 8

Os recursos do Java 8 podem simplificar nossa tentativa acima de obter o valor máximo deMap em mais de uma maneira.

3.1. UsandoCollections.max() com uma expressão Lambda

Vamos começar explorando como as expressões lambda podem simplificar a chamada paraCollections.max():

public > V maxUsingCollectionsMaxAndLambda(Map map) {
    Entry maxEntry = Collections.max(map.entrySet(), (Entry e1, Entry e2) -> e1.getValue()
        .compareTo(e2.getValue()));
    return maxEntry.getValue();
}

Como podemos ver aqui,lambda expressions save us from defining the full-fledged functional interfacee fornecem uma forma concisa de definir a lógica. Para ler mais sobre as expressões lambda, verifique tambémour previous article.

3.2. UsandoStream

A APIStream é outra adição aJava 8 que simplificou muito o trabalho com coleções:

public > V maxUsingStreamAndLambda(Map map) {
    Optional> maxEntry = map.entrySet()
        .stream()
        .max((Entry e1, Entry e2) -> e1.getValue()
            .compareTo(e2.getValue())
        );

    return maxEntry.get().getValue();
}

Esta API oferece muitas consultas de processamento de dados como transformações demap-reduce em coleções. Here, we’ve used max() over a stream of Map Entry que é um caso especial de uma operação de redução. Mais detalhes sobre a APIStream disponíveishere.

Também estamos utilizando a APIOptional aqui, que é um objeto de contêiner adicionado em Java 8 que pode ou não conter um valor não nulo. Mais detalhes sobreOptional podem ser obtidoshere.

3.3. UsandoStream com Referência de Método

Por fim, vamos ver como as referências de método podem simplificar ainda mais nosso uso de expressões lambda:

public > V maxUsingStreamAndMethodReference(Map map) {
    Optional> maxEntry = map.entrySet()
        .stream()
        .max(Comparator.comparing(Map.Entry::getValue));
    return maxEntry.get()
        .getValue();
}

Nos casos em que expressões lambda estão apenas chamando um método existente, uma referência de método nos permite fazer isso usando o nome do método diretamente. Para obter mais detalhes sobre method references, dê uma olhada emthis previous article.

4. Conclusão

Neste artigo, vimos várias maneiras de encontrar o valor mais alto em aJava Map, algumas das quais usando recursos adicionados como parte do Java 8.

Como sempre, o código dos exemplos está disponívelover on GitHub.