Java Streams - Java Stream Map








A map operation applies a function to each element to produce another stream.

The number of elements in the input and output streams is the same.

The operation does not modify the elements of the input stream.

You can apply the map operation on a stream using one of the following methods of the Stream<T> interface:

<R> Stream<R> map(Function<? super T,? extends R> mapper)
DoubleStream  mapToDouble(ToDoubleFunction<? super T> mapper)
IntStream     mapToInt(ToIntFunction<? super T> mapper)
LongStream    mapToLong(ToLongFunction<? super T> mapper)

IntStream, LongStream and DoubleStream also define map functions. The methods supporting the map operation on an IntStream are as follows:

IntStream     map(IntUnaryOperator mapper)
DoubleStream  mapToDouble(IntToDoubleFunction mapper)
LongStream    mapToLong(IntToLongFunction   mapper)
<U> Stream<U> mapToObj(IntFunction<? extends  U>  mapper)

The following code shows how to use map() to map the elements from IntStream to their squares, and prints the mapped stream on the standard output.

import java.util.stream.IntStream;
//from  w  w w. j a v  a  2 s.c  o m
public class Main {
  public static void main(String[] args) {
    IntStream.rangeClosed(1, 5)
             .map(n -> n * n)
             .forEach(System.out::println);

  }
}

The code above generates the following result.





Example 2

The following code maps a stream of employees to their names and prints the mapped stream.

import java.time.LocalDate;
import java.time.Month;
import java.util.Arrays;
import java.util.List;
//from w  ww.  j  a  v a2s  .  c o m
public class Main {
  public static void main(String[] args) {
    Employee.persons()
            .stream()
            .map(Employee::getName)
            .forEach(System.out::println);
  }
}

class Employee {
  public static enum Gender {
    MALE, FEMALE
  }

  private long id;
  private String name;
  private Gender gender;
  private LocalDate dob;
  private double income;

  public Employee(long id, String name, Gender gender, LocalDate dob,
      double income) {
    this.id = id;
    this.name = name;
    this.gender = gender;
    this.dob = dob;
    this.income = income;
  }

  public long getId() {
    return id;
  }

  public void setId(long id) {
    this.id = id;
  }

  public String getName() {
    return name;
  }

  public void setName(String name) {
    this.name = name;
  }

  public Gender getGender() {
    return gender;
  }

  public boolean isMale() {
    return this.gender == Gender.MALE;
  }

  public boolean isFemale() {
    return this.gender == Gender.FEMALE;
  }

  public void setGender(Gender gender) {
    this.gender = gender;
  }

  public LocalDate getDob() {
    return dob;
  }

  public void setDob(LocalDate dob) {
    this.dob = dob;
  }

  public double getIncome() {
    return income;
  }

  public void setIncome(double income) {
    this.income = income;
  }

  public static List<Employee> persons() {
    Employee p1 = new Employee(1, "Jake", Gender.MALE, LocalDate.of(1971,
        Month.JANUARY, 1), 2343.0);
    Employee p2 = new Employee(2, "Jack", Gender.MALE, LocalDate.of(1972,
        Month.JULY, 21), 7100.0);
    Employee p3 = new Employee(3, "Jane", Gender.FEMALE, LocalDate.of(1973,
        Month.MAY, 29), 5455.0);
    Employee p4 = new Employee(4, "Jode", Gender.MALE, LocalDate.of(1974,
        Month.OCTOBER, 16), 1800.0);
    Employee p5 = new Employee(5, "Jeny", Gender.FEMALE, LocalDate.of(1975,
        Month.DECEMBER, 13), 1234.0);
    Employee p6 = new Employee(6, "Jason", Gender.MALE, LocalDate.of(1976,
        Month.JUNE, 9), 3211.0);

    List<Employee> persons = Arrays.asList(p1, p2, p3, p4, p5, p6);

    return persons;
  }

  @Override
  public String toString() {
    String str = String.format("(%s, %s,  %s,  %s,  %.2f)\n", id, name, gender,
        dob, income);
    return str;
  }
}

The code above generates the following result.





Streams flatMap

Streams map() operation creates a one-to-one mapping.

Streams flatMap() supports one-to-many mapping. It maps each element to a stream and then flaten the stream of streams to a stream.

The following code maps a stream of three numbers: 1, 2, and 3 to produce a stream that contains the numbers and their next numbers. The output stream should be 1,2,2,3,3,4.

import java.util.stream.Stream;
/*  ww w .  j a  v a 2 s.co  m*/
public class Main {
  public static void main(String[] args) {
    Stream.of(1, 2, 3)
    .flatMap(n -> Stream.of(n, n+1))
    .forEach(System.out::println);

  }
}

The code above generates the following result.

Example 3

The following code shows how to convert a stream of strings to a stream of characters.

import java.util.stream.Stream;
// w  w  w .  j  a v a 2s . com
public class Main {
  public static void main(String[] args) {
    Stream.of("XML", "Java",  "CSS")
        .map(name  ->  name.chars())
        .flatMap(intStream ->  intStream.mapToObj(n ->  (char)n))
        .forEach(System.out::println); 

  }
}

The code maps the strings to IntStream returns from chars() method of the String class.

The output of the map() method is Stream<IntStream>.

The flatMap() method maps the Stream<IntStream> to Stream<Stream<Character>> and finally, flattens it to produce a Stream<Character>.

The code above generates the following result.

Example 4

The following code flatMaps the stream of string values to a IntStreams, then maps IntStream to Stream of characters.

import java.util.stream.IntStream;
import java.util.stream.Stream;
// www  .  j  a  v a 2s.  c  o  m
public class Main {
  public static void main(String[] args) {
    Stream.of("XML", "Java",  "CSS")
        .flatMap(name ->  IntStream.range(0, name.length())
        .mapToObj(name::charAt))
        .forEach(System.out::println);
  }
}

The code above generates the following result.