Related practice problems: Functional-2
"Functional" programming in Java (and other languages) is a great technique that can solve certain problem types with just 1 or 2 lines of code. This section looks at "filtering" added to mapping.
Filtering uses a lambda to decide which items should be kept or removed from a collection.
In Java, the removeIf( lambda )
takes a lambda function which takes in a single item, and returns boolean true if it should be removed, and false otherwise.
As a first example, we'll use the "noNeg" problem: given a list of integers, returns a list of the integers, omitting any which are less than 0. Here is the noNeg solution code:
public List<Integer> noNeg(List<Integer> nums) { nums.removeIf(n -> n < 0); return nums; }
The list.removeIf( lambda ); method does all the work, removing any items where the lambda function returns true:
The lambda function n -> n < 0
has the parameter n
and its boolean expression n < 0
is true when the n is less than 0, and so should be removed.
Try a few of these practice problems using the .removeIf() pattern. Remember, the lambda takes in a regular item, and evaluates to a boolean.
practice: noNeg - the noNeg problem shown above
practice: noTeen - remove "teen" numbers
practice: noZ - remove strings containing "z"
The obvious next step is mapping the items in a list first, and then filtering the resulting values. This can be done with 2 lines of code: nums.replaceAll(...) to do the mapping, and then nums.removeIf(...) to filter the resulting values. Here is a practice problem:
practice: two2 - Given a list of non-negative integers, return a list of those numbers multiplied by 2, omitting any of the resulting numbers that end in 2.
The Java stream system provides more complicated mapping and filtering. Here is the solution to noNeg() using Java streams. Note that the filter() function has the opposite boolean logic as removeIf(): true means keep the element, false means remove it. A .map() stage can be inserted before or after the .filter() to combine mapping and filtering.
public List<Integer> noNeg(List<Integer> nums) { return nums.stream() .filter(n -> n >= 0) .collect(Collectors.toList()); }
For more about streams, see the Java Stream Docs
CodingBat.com code practice. Copyright 2017 Nick Parlante.