How to get the first element of the List or Set?

808,432

Solution 1

See the javadoc

of List

list.get(0);

or Set

set.iterator().next();

and check the size before using the above methods by invoking isEmpty()

!list_or_set.isEmpty()

Solution 2

In Java >=8 you could also use the Streaming API:

Optional<String> first = set.stream().findFirst();

(Useful if the Set/List may be empty.)

Solution 3

Let's assume that you have a List<String> strings that you want the first item from.

There are several ways to do that:

Java (pre-8):

String firstElement = null;
if (!strings.isEmpty() && strings.size() > 0) {
    firstElement = strings.get(0);
}

Java 8:

Optional<String> firstElement = strings.stream().findFirst();

Guava

String firstElement = Iterables.getFirst(strings, null);

Apache commons (4+)

String firstElement = (String) IteratorUtils.get(strings, 0);

Apache commons (before 4)

String firstElement = (String) CollectionUtils.get(strings, 0);

Followed by or encapsulated within the appropriate checks or try-catch blocks.

Kotlin:

In Kotlin both Arrays and most of the Collections (eg: List) have a first method call. So your code would look something like this

for a List:

val stringsList: List<String?> = listOf("a", "b", null)
val first: String? = stringsList.first()

for an Array:

val stringArray: Array<String?> = arrayOf("a", "b", null)
val first: String? = stringArray.first()

Followed by or encapsulated within the appropriate checks or try-catch blocks.

Kotlin also includes safer ways to do that for kotlin.collections, for example firstOrNull or getOrElse, or getOrDefault when using JRE8

Solution 4

I'm surprised that nobody suggested guava solution yet:

com.google.common.collect.Iterables.get(collection, 0)
// or
com.google.common.collect.Iterables.get(collection, 0, defaultValue)
// or
com.google.common.collect.Iterables.getFirst(collection, defaultValue)

or if you expect single element:

com.google.common.collect.Iterables.getOnlyElement(collection, defaultValue)
// or
com.google.common.collect.Iterables.getOnlyElement(collection)

Solution 5

and further

Set<String> set = new TreeSet<>();
    set.add("2");
    set.add("1");
    set.add("3");
    String first = set.stream().findFirst().get();

This will help you retrieve the first element of the list or set. Given that the set or list is not empty (get() on empty optional will throw java.util.NoSuchElementException)

orElse() can be used as: (this is just a work around - not recommended)

String first = set.stream().findFirst().orElse("");
set.removeIf(String::isEmpty);

Below is the appropriate approach :

Optional<String> firstString = set.stream().findFirst();
if(firstString.isPresent()){
    String first = firstString.get();
}

Similarly first element of the list can be retrieved.

Hope this helps.

Share:
808,432
user496949
Author by

user496949

Updated on April 03, 2020

Comments

  • user496949
    user496949 about 4 years

    I'd like to know if I can get the first element of a list or set. Which method to use?

  • Steve Kuo
    Steve Kuo over 12 years
    Use isEmpty() instead of size()>0. It better shows your intent and is possibly more efficient (e.g. LinkList size() is O(n)).
  • efritz
    efritz about 10 years
    @SteveKuo LinkedList has a size variable so size() is O(1). Additionally, isEmpty() is implemented as size() == 0.
  • Guido Medina
    Guido Medina about 9 years
    Always use List.iterator().next() or Set.iterator().next() to avoid O(N) for Linked data structures, you never know what implementation you will be receiving, and of course verify by using Set.isEmpty() or List.isEmpty() for the same reason, for both cases will always be O(1) instead of a potential O(N) if, again, an implementation of Linked data structure is passed liked LinkedList or LinkedHashSet
  • dpedro
    dpedro about 8 years
    set.toArray()[0] will have to pass through whole set contents to create an array to get only the first element, which is not very effective.
  • Diablo
    Diablo almost 8 years
    This looks great but without get() I couldn't be able to call resultant element specific methods.set.stream().findFirst().get() will allow you to call any methods on the resultant object. eg:set.stream().findFirst().get().getMessage()
  • Arturas M
    Arturas M over 7 years
    This should be the accepted answer, although not too verbose, but gives the most accurate answer and works perfectly!
  • Magnilex
    Magnilex about 7 years
    @Diablo Be careful though, because get() will throw an exception if the optional is empty. There are plenty of other methods on Optional that might be more suitable.
  • ZetaPR
    ZetaPR about 7 years
    this will cause a very low performance
  • ciekawy
    ciekawy almost 7 years
    good to have an access to the first method yet here the question concerns list/set regardless the order.
  • molholm
    molholm almost 7 years
    I know, the question had been answered when i posted this, it is just meant as related information. My thought was that it would be likely that someone looking for an answer to this in some cases would want to work with sorted objects. I edited my answer.
  • troosan
    troosan over 6 years
    if you want it to return null, just do String first = set.stream().findFirst().orElse(null);
  • Paul
    Paul about 6 years
    For a set this method returns an Object and not the type of element in the Set.
  • Ruslan Stelmachenko
    Ruslan Stelmachenko about 6 years
    @troosan This is still isn't null-safe because the first element of the set can be null, in which case findFirst() will throw NPE. The null-safe way is to use something like: set.stream().map(Optional::ofNullable).findFirst().orElseGet‌​(Optional::empty).or‌​Else(null). First, we wrap first element of the stream into Optional, then, after findFirst() (which wraps our Optional into another Optional) we unwrap it back or return Optional.empty() if Set was empty. Then, finally, we return the first element of Set or null.
  • troosan
    troosan about 6 years
    @djxak indeed you are right, your proposal is of course safer if you are not sure what the set contains (and what Implementation of the Set is used)
  • CrazyGreenHand
    CrazyGreenHand over 3 years
    "If the stream has no encounter order, then any element may be returned"(docs.oracle.com/javase/8/docs/api/java/util/stream‌​/Stream.html)
  • CrazyGreenHand
    CrazyGreenHand over 3 years
    "If the stream has no encounter order, then any element may be returned" (docs.oracle.com/javase/8/docs/api/java/util/stream/Stream.h‌​tml)
  • Mikołaj Podbielski
    Mikołaj Podbielski about 3 years
    @RuslanStelmachenko Can you elaborate on throwing NPE?
  • Mikołaj Podbielski
    Mikołaj Podbielski about 3 years
    System.out.println(new HashSet<>().stream().findFirst().orElse(null)); just prints null
  • Ruslan Stelmachenko
    Ruslan Stelmachenko about 3 years
    @MikołajPodbielski As I wrote, it will throw NPE only if the first element of the set is null. Your example uses empty set. It's fine. But try to do hashSet.add(null) before you create a stream from it. See findFirst() docs on the topic when it throws NPE.