ZetCode

Java Stream filter

last modified January 27, 2024

Java Stream filter tutorial shows how to filter Java streams using filtering operations.

Java Stream

Java Stream is a sequence of elements from a source that supports aggregate operations. Streams do not store elements; the elements are computed on demand. Elements are consumed from data sources such as collections, arrays, or I/O resources.

Stream aggregate operations are similar to SQL operations. We can apply filtering, mapping, reducing, matching, searching, or sorting operations on streams. Streams allow chaining of multiple stream operations. Unlike collections which use external iterations, streams are iterated internally.

Java Stream filter

Java Stream filter method is an intermediate operation, which returns elements of the stream that match the given predicate. A predicate is a function that returns a boolean value.

Java Stream filter string length

The following example filters a list of strings.

com/zetcode/StreamFilterEx.java
package com.zetcode;

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

public class StreamFilterEx {

    public static void main(String[] args) {

        List<String> words = List.of("pen", "custom", "orphanage",
                "forest", "bubble", "butterfly");

        List<String> result = words.stream().filter(word -> word.length() > 5)
                .collect(Collectors.toList());

        result.forEach(word -> System.out.println(word));
    }
}

We have a list of words. We filter the list to include only strings whose length is bigger than five.

List<String> result = words.stream().filter(word -> word.length() > 5)
        .collect(Collectors.toList());

With the stream method, we create a Java Stream from a list of strings. On this stream, we apply the filter method. The filter method accepts an anonymous functions that returns a boolean true for all elements of the stream whose length is bigger that five. We create a list back from the stream with the collect method.

result.forEach(word -> System.out.println(word));

We go through the result with the forEach method and print all its elements to the console.

$ java com/zetcode/StreamFilterEx.java
custom
orphanage
forest
bubble
butterfly

Java Stream filter null values

The next example filters out null values.

com/zetcode/StreamFilterRemoveNulls.java
package com.zetcode;

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

public class StreamFilterRemoveNulls {

    public static void main(String[] args) {

        List<String> words = Arrays.asList("cup", null, "forest",
                "sky", "book", null, "theatre");

        List<String> result = words.stream().filter(w -> w != null)
                .collect(Collectors.toList());

        System.out.println(result);
    }
}

We have a list of words. With the Stream filtering operation, we create a new list with null values removed.

List<String> result = words.stream().filter(w -> w != null)
        .collect(Collectors.toList());

In the body of the lambda expression, we check that the value is not null. The collect method is a terminal operation that creates a list from the filtered stream.

Java Stream multiple filter operations

It is possible to apply multiple filter operations on a stream.

com/zetcode/StreamMultipleFilters.java
package com.zetcode;

import java.util.Arrays;
import java.util.function.IntConsumer;

public class StreamMultipleFilters {

    public static void main(String[] args) {

        int[] inums = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 };
        
        IntConsumer icons = i -> System.out.print(i + " ");
        
        Arrays.stream(inums).filter(e -> e < 6 || e > 10)
                .filter(e -> e % 2 == 0).forEach(icons);
    }
}

In the example, we apply multiple filter operations on a stream of integers.

int[] inums = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 };

We have an array of integer values.

IntConsumer icons = i -> System.out.print(i + " ");

IntConsumer is an operation that accepts a single integer value argument and returns no result.

Arrays.stream(inums).filter(e -> e < 6 || e > 10)
        .filter(e -> e % 2 == 0).forEach(icons);

A stream is created from the array with the Arrays.stream method. Multiple filtering operations are performed.

Java Stream filter objects

The next example shows how to filter objects.

com/zetcode/StreamFilterObjects.java
package com.zetcode;

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

public class StreamFilterObjects {

    public static void main(String[] args) {

        List<User> persons = List.of(
                new User("Jack", "[email protected]"),
                new User("Peter", "[email protected]"),
                new User("Lucy", "[email protected]"),
                new User("Robert", "[email protected]"),
                new User("Martin", "[email protected]")
        );

        List<User> result = persons.stream()
                .filter(person -> person.email().matches(".*post\\.com"))
                .collect(Collectors.toList());

        result.forEach(p -> System.out.println(p.name()));
    }
}

record User(String name, String email) {}

The example creates a stream of User objects. It filters those which match a specific regular expression.

List<User> result = persons.stream()
        .filter(person -> person.getEmail().matches(".*post\\.com"))
        .collect(Collectors.toList());

In the filter predicate, we choose emails that match the .*post\\.com pattern.

Java Stream filter map by keys

In the following example, we filter a map by its keys.

com/zetcode/JavaStreamFilterMapByValues.java
package com.zetcode;

import java.util.HashMap;
import java.util.Map;

public class JavaStreamFilterMapByKeys {

    public static void main(String[] args) {

        Map<String, String> hmap = new HashMap<>();
        
        hmap.put("de", "Germany");
        hmap.put("hu", "Hungary");
        hmap.put("sk", "Slovakia");
        hmap.put("si", "Slovenia");
        hmap.put("so", "Somalia");
        hmap.put("us", "United States");
        hmap.put("ru", "Russia");
        
        hmap.entrySet().stream().filter(map -> map.getKey().startsWith("s"))
                .forEach(m -> System.out.println(m));
    }
}

The example filters domain names starting with s letter.

Java Stream filter map by values

In the following example, we filter a map by its values.

com/zetcode/StreamFilterMapByValues.java
package com.zetcode;

import java.util.HashMap;
import java.util.Map;

public class StreamFilterMapByValues {

    public static void main(String[] args) {

        Map<String, String> hmap = new HashMap<>();

        hmap.put("de", "Germany");
        hmap.put("hu", "Hungary");
        hmap.put("sk", "Slovakia");
        hmap.put("si", "Slovenia");
        hmap.put("so", "Somalia");
        hmap.put("us", "United States");
        hmap.put("ru", "Russia");

        hmap.entrySet().stream().filter(map -> map.getValue().equals("Slovakia")
                || map.getValue().equals("Slovenia"))
                .forEach(m -> System.out.println(m));
    }
}

In the example, we filter out two countries from the map.

Source

Java Stream documentation

In this article we have have worked with Java Stream filtering operations.

Author

My name is Jan Bodnar and I am a passionate programmer with many years of programming experience. I have been writing programming articles since 2007. So far, I have written over 1400 articles and 8 e-books. I have over eight years of experience in teaching programming.

List all Java tutorials.