Skip to main content Link Menu Expand (external link) Document Search Copy Copied

Intermediate and Terminal Operations in Java Streams

Header Image

Ahoy there, me hearty! Today, we’re going to be delving into the world of Java Streams once again. We’ve already talked about what Java Streams are and why they’re useful, so let’s jump right into the topic of intermediate and terminal operations.

Definition of Intermediate and Terminal Operations

Now, before we get into the nitty-gritty details of intermediate and terminal operations, let’s first define what they are. In Java Streams, intermediate operations are operations that transform a stream into another stream. They don’t produce a final result, but rather create a new stream that can be operated on further.

On the other hand, terminal operations are operations that produce a result or a side-effect. When a terminal operation is invoked on a stream, it consumes the stream and produces a result or a side-effect, such as printing to the console.

To put it in pirate terms, intermediate operations are like a crew member who takes the wheel and sets the course for the ship. They don’t get us to our final destination, but they’re essential in guiding us there. Terminal operations, on the other hand, are like the captain who gives the final orders to dock the ship and unload the cargo.

Examples of Intermediate and Terminal Operations

Now that we know what intermediate and terminal operations are, let’s take a look at some examples. Here are a few common intermediate operations in Java Streams:

  • filter(Predicate<T> predicate) - filters the stream based on a given predicate
  • map(Function<T, R> mapper) - maps the elements of the stream to a new type using the given mapper function
  • flatMap(Function<T, Stream<R>> mapper) - maps each element of the stream to a new stream using the given mapper function, and then flattens the resulting streams into a single stream

And here are a few common terminal operations in Java Streams:

  • count() - returns the number of elements in the stream
  • findFirst() - returns the first element in the stream
  • forEach(Consumer<T> action) - performs the given action for each element in the stream

So, there you have it, matey! Now you know what intermediate and terminal operations are in Java Streams. In the next section, we’ll dive into some examples of how to use these operations to manipulate and process streams.

Examples of Intermediate and Terminal Operations (Continued)

Now that we have a better understanding of what intermediate and terminal operations are, let’s take a look at some examples of how we can use them in Java Streams.

Example 1: Filtering and Counting

Suppose we have a list of plundered treasure, and we want to filter out all the gold coins and count the number of remaining treasures. We can use the filter and count methods to accomplish this task.

List<Treasure> treasures = // list of plundered treasure
long numNonGoldTreasures = treasures.stream()
                                    .filter(t -> !t.getType().equals("gold coin"))
                                    .count();
System.out.println("Number of non-gold treasures: " + numNonGoldTreasures);

In this example, the filter method is used to exclude all the gold coins from the stream, and the resulting stream is then passed to the count method, which returns the number of remaining treasures.

Example 2: Mapping and Reducing

Let’s say we have a list of pirate crew members, and we want to calculate the total number of years of experience they have. We can use the map and reduce methods to accomplish this task.

List<Pirate> crew = // list of pirate crew members
int totalYearsExperience = crew.stream()
                                .map(Pirate::getYearsExperience)
                                .reduce(0, Integer::sum);
System.out.println("Total years of experience: " + totalYearsExperience);

In this example, the map method is used to extract the years of experience for each pirate crew member, and the resulting stream of integers is then passed to the reduce method, which adds up all the years of experience to produce a final result.

Conclusion

Intermediate and terminal operations are essential concepts in Java Streams that allow us to manipulate and process streams of data. By using intermediate operations to transform streams into new streams, and terminal operations to produce final results or side-effects, we can write concise and expressive code that is both efficient and readable.

So, me hearties, that concludes our discussion on intermediate and terminal operations in Java Streams. We hope you found this article informative and entertaining. Until next time, keep hoisting the Jolly Roger and plundering the high seas!