Categories
Articles Java Java Interview Questions

Java 8 – Method Reference – Is it Magic?

Amongst the notable features in Java8, Method Reference adds Shorthand syntax for a lambda expression. In most cases, Lambda expression does nothing more than just calling a single method. If you find yourself doing that most often, its time to look at Method reference. It can be used to replace entire Lambda expression, let’s have a look at following example

class Student {
  int rollNo;
  String name;
  LocalDate birthDate;

//Getter and setter goes here.
}

The Student class captures basic details like Roll Number, Birth Date and Student name. Let’s define a collection to store some student information

public class StudentApplication {
  public static void main(String[] args) {
    List students = new ArrayList<>();
    students.add(createStudent("Michael Freit", 122, LocalDate.of(1998, 05, 12)));
    students.add(createStudent("Jeremy Kahn", 110, LocalDate.of(1998, 01, 03)));
    students.add(createStudent("Hugo Patrick", 95, LocalDate.of(1998, 03, 24)));
    students.add(createStudent("Nathan Hendrige", 130, LocalDate.of(1998, 02, 18)));
    students.add(createStudent("Kate hudson", 117, LocalDate.of(1998, 04, 10)));
  }

  private static Student createStudent(String name, int rollNo, LocalDate dateOfBirth) {
    Student student = new Student();
    student.setName(name);
    student.setRollNo(rollNo);
    student.setDateOfBirth(dateOfBirth);
    return student;
  }
}

What if you wish to simply print name of each student from the list. The pre-Java 8 syntax will be like

for(Student s : students){
  System.out.println(student.getName());
}

Using Java 8, Lambda expression syntax will look like below

students.stream().map(student -> student.getName()).forEach(s->System.out.println(s));

With Method expression, the code will look like

students.stream().map(Student::getName).forEach(System.out::println);

Notice student -> student.getName() is replaced with Student::getName and s->System.out.println(s) with System.out::println. In each of the Lambda expression, a single method was replaced with equivalent Method reference. Student::getName is a method reference of a defined type and System.out::println is an instance method of PrintStream object. In addition to that there are two more kinds.

  • Static method reference
  • Constructor reference

Static method reference
Static method reference requires a name of the class followed by the method name

Class::method

Let’s understand it by writing some code.

public class Library {
  public static void main(String[] args) {
    List shelf = new ArrayList<>();
    shelf.add("Blockchain revolution");
    shelf.add("Start with WHY?");
    shelf.add("Flying without Net");
  }

  private static void printBookName(String name) {
    System.out.println(name)
  }
}

To print name of each book

Java 7 or before

for(String book : shelf) {
  printBookName(book);
}

Java 8 with lambda

shelf.stream().forEach(s -> printBookName(s));

With Java 8 method reference

shelf.stream().forEach(Library::printBookName);

Constructor with new
This one is very easy, instead of using

new Integer();

use

Integer::new

So based on above examples Method Reference can be summarised as

Kind Pre-Java 8 Java 8
Static Method Class.staticMethod(); Class::staticMethod
Instance Method object.instanceMethod() object::instanceMethod
Instance Method of Specific Type sampleMethod(obj, args) { obj.callMe(args); } ObjectType::callMe
Constructor new SomeClass() SomeClass::new

That’s not all about Method Reference. Refer below example of how a thread can be created using a Method reference

public class ThreadDemo {
  public static void main(String[] args) {
    //Pre-Java 8
    Thread t = new Thread(new Runnable(){
      public void run(){
        ThreadDemo.printName();
      }
    });
    t.start();

   //Java8-Lambda
   Thread t2 = new Thread(()-> ThreadDemo.printName());
   t2.start();

   //Java8-Method reference
   Thread t3 = new Thread(ThreadDemo::printName);
   t3.start();
  }

  private static void printName(){
    System.out.println("I am inside Thread!!!");
  }
}

In next article, we will explore more about java.util.function package and identify how it fits with MethodReference and Lambda.

By Carbon Rider

Hi this is Yogesh, welcome to my world. Being passionate about learning new technologies and building frameworks, I end up spending most of my time in front of computer. But over last few months, I realised apart from being good coder and designer (Yes I am) I have something hidden in me. And thats called ART.

Leave a Reply