Як отримати максимальне значення з колекції (наприклад, ArrayList)?


134

Існує ArrayList, який зберігає цілі значення. Мені потрібно знайти максимальне значення в цьому списку. Напр. Припустімо, що збережені значення arrayList є: 10, 20, 30, 40, 50і максимальне значення було б 50.

Який ефективний спосіб знайти максимальне значення?

@Edit: Я щойно знайшов одне рішення, в якому я не дуже впевнений

ArrayList<Integer> arrayList = new ArrayList<Integer>();
arrayList.add(100); /* add(200), add(250) add(350) add(150) add(450)*/

Integer i = Collections.max(arrayList)

і це повертає найвище значення.

Інший спосіб порівняння кожного значення, наприклад selection sort or binary sort algorithm  


2
Чи намагалися ви знайти значення? Де ти застряг? Можливо, ваше власне рішення занадто неефективне?
— Ентоні Пеграм

1
Якщо це щось, що ви робите багато, Java скомпілює його до складання, тому, якщо ви не зробите щось нерозумно, ваш код буде досить ефективним за допомогою простого ітератора.
— Білл К

@AnthonyPegram: я маю на увазі який алгоритм сортування чи є якийсь метод у Java? Доречі перевірити відповідь гетоманців.
— користувач1010399

Для масиву , який може містити nullзначення: stackoverflow.com/questions/369383 / ...
— Чіро Сантіллі郝海东冠状病六四事件法轮功

Відповіді:


292

Ви можете використовувати це Collections APIдля того, щоб легко досягти бажаного - читайте ефективно - достатньо Javadoc для Collections.max

Collections.max(arrayList);

Повертає максимальний елемент даної колекції відповідно до природного впорядкування її елементів. Усі елементи колекції повинні реалізовувати інтерфейс Comparable.


8
Чому це прийнята відповідь? Це не найефективніше рішення. Найкращий випадок, це O (n log (n)) і вибирати максимум, перевіряючи їх, все лише O (n)
— Брендан Лонг

Так, повторення через список є, O(n log(n))але якщо "Не існує особливо ефективного способу", що ви пропонуєте, що це краще рішення, окрім перевірки їх усіх?
— getomanners

Наївно повторення швидше (перевірено, компаратор отримує бали з карти), ніж сортування та отримання першого елемента або використання макс. Обидва сортування + беруть перший, а макс використовували лямбда.
— majTheHero

31

Це питання майже рік, але я виявив, що якщо ви зробите спеціальний компаратор для об'єктів, ви можете використовувати Collections.max для списку масивів об’єктів.

import java.util.Comparator;

public class compPopulation implements Comparator<Country> {
    public int compare(Country a, Country b) {
        if (a.getPopulation() > b.getPopulation())
            return -1; // highest value first
        if (a.getPopulation() == b.Population())
            return 0;
        return 1;
    }
}
ArrayList<Country> X = new ArrayList<Country>();
// create some country objects and put in the list
Country ZZ = Collections.max(X, new compPopulation());

вам потрібен спеціальний компаратор для типів календаря?
— tatmanblue

Ваш код поверне найменше значення у списку, якщо (a.getPopulation ()> b.getPopulation ()) повернути -1; Вищезазначене має змінитись, якщо (a.getPopulation () <b.getPopulation ()) повернути -1; // Перша найвища цінність
— Чандракант Гоуда

Це можна зробити і за допомогою лямбда: maxElement = Collections.max (колекція, (el1, el2) -> el1 - el2);
— majTheHero

22
public int getMax(ArrayList list){
    int max = Integer.MIN_VALUE;
    for(int i=0; i<list.size(); i++){
        if(list.get(i) > max){
            max = list.get(i);
        }
    }
    return max;
}

Наскільки я розумію, це в основному те, що робить Collections.max (), хоча вони використовують компаратор, оскільки списки є загальними.


Це швидше за все для мого випадку.
— majTheHero

14

Ми можемо просто використовувати Collections.max()і Collections.min()методи.

public class MaxList {
    public static void main(String[] args) {
        List l = new ArrayList();
        l.add(1);
        l.add(2);
        l.add(3);
        l.add(4);
        l.add(5);
        System.out.println(Collections.max(l)); // 5
        System.out.println(Collections.min(l)); // 1
    }
}

8

Клас Integer реалізує Порівнянні. Тому ми можемо легко отримати максимальне або мінімальне значення у списку Integer.

public int maxOfNumList() {
    List<Integer> numList = new ArrayList<>();
    numList.add(1);
    numList.add(10);
    return Collections.max(numList);
}

Якщо клас не реалізує Порівняльне, і нам потрібно знайти максимальне та мінімальне значення, тоді ми повинні написати власний Порівняльник.

List<MyObject> objList = new ArrayList<MyObject>();
objList.add(object1);
objList.add(object2);
objList.add(object3);
MyObject maxObject = Collections.max(objList, new Comparator<MyObject>() {
    @Override
    public int compare(MyObject o1, MyObject o2) {
        if (o1.getValue() == o2.getValue()) {
            return 0;
        } else if (o1.getValue() > o2.getValue()) {
            return -1;
        } else if (o1.getValue() < o2.getValue()) {
            return 1;
        }
        return 0;
    }
});

7

Comparator.comparing

У Java 8 колекції були розширені за допомогою лямбда. Тож знаходження максимуму та хв можна здійснити наступним чином, використовуючи Comparator.comparing:

Код:

List<Integer> ints = Stream.of(12, 72, 54, 83, 51).collect(Collectors.toList());
System.out.println("the list: ");
ints.forEach((i) -> {
    System.out.print(i + " ");
});
System.out.println("");
Integer minNumber = ints.stream()
        .min(Comparator.comparing(i -> i)).get();
Integer maxNumber = ints.stream()
        .max(Comparator.comparing(i -> i)).get();

System.out.println("Min number is " + minNumber);
System.out.println("Max number is " + maxNumber);

Вихід:

 the list: 12 72 54 83 51  
 Min number is 12 
 Max number is 83

5

Немає особливо ефективного способу знайти максимальне значення у несортованому списку - потрібно лише перевірити їх усі та повернути найвище значення.


що з цим цілим i = Collections.max(arrayList). він повертає найвище значення в моєму випадку, чи я не дуже впевнений. що ти кажеш?
— користувач1010399

@ user1010399 - Це саме те, що я говорю - перевіряє кожне значення і повертає найвище.
— Брендан Довгий

гаразд, гаразд. Дякую. Я трохи розгубився між цим методом колекції та алгоритмом сортування.
— користувач1010399

4

Ось ще три способи знайти максимальне значення у списку, використовуючи потоки:

List<Integer> nums = Arrays.asList(-1, 2, 1, 7, 3);
Optional<Integer> max1 = nums.stream().reduce(Integer::max);
Optional<Integer> max2 = nums.stream().max(Comparator.naturalOrder());
OptionalInt max3 = nums.stream().mapToInt(p->p).max();
System.out.println("max1: " + max1.get() + ", max2: " 
   + max2.get() + ", max3: " + max3.getAsInt());

Усі ці методи, як і Collections.max, повторюють всю колекцію, отже, вони вимагають часу, пропорційного розміру колекції.


3

Java 8

Як цілі числа порівнянні, ми можемо використовувати наступний один вкладиш у:

List<Integer> ints = Stream.of(22,44,11,66,33,55).collect(Collectors.toList());
Integer max = ints.stream().mapToInt(i->i).max().orElseThrow(NoSuchElementException::new); //66
Integer min = ints.stream().mapToInt(i->i).min().orElseThrow(NoSuchElementException::new); //11

Ще одне зауваження - ми не можемо використовувати Funtion.identity()замість того, i->iяк mapToIntочікує, ToIntFunctionщо це зовсім інший інтерфейс і не пов'язаний з ним Function. Більше того, у цього інтерфейсу є лише один метод applyAsIntі жоден identity()метод.


1

Ось фукція

public int getIndexOfMax(ArrayList<Integer> arr){
    int MaxVal = arr.get(0); // take first as MaxVal
    int indexOfMax = -1; //returns -1 if all elements are equal
    for (int i = 0; i < arr.size(); i++) {
        //if current is less then MaxVal
        if(arr.get(i) < MaxVal ){
            MaxVal = arr.get(i); // put it in MaxVal
            indexOfMax = i; // put index of current Max
        }
    }
    return indexOfMax;  
}

1
package in.co.largestinarraylist;

import java.util.ArrayList;
import java.util.Scanner;

public class LargestInArrayList {

    public static void main(String[] args) {

        int n;
        ArrayList<Integer> L = new ArrayList<Integer>();
        int max;
        Scanner in = new Scanner(System.in);
        System.out.println("Enter Size of Array List");
        n = in.nextInt();
        System.out.println("Enter elements in Array List");

        for (int i = 0; i < n; i++) {
            L.add(in.nextInt());
        }

        max = L.get(0);

        for (int i = 0; i < L.size(); i++) {
            if (L.get(i) > max) {
                max = L.get(i);
            }
        }

        System.out.println("Max Element: " + max);
        in.close();
    }
}




-3

залежно від розміру масиву багатопотокове рішення також може прискорити роботу


Це звучить скоріше як коментар, ніж фактична відповідь на питання.
— Pac0
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.