lang

MethodHandle example

public class MethodAccessExampleWithArgs {
 private final int i;
 
 public MethodAccessExampleWithArgs(int i_) {
  i = i_;
 }
 
 private void bar(int j, String msg) {
  System.out.println("Private Method 'bar' successfully accessed : "
    + i + ", " + j + " : " + msg + "!");
 }
 
 // Using Reflection
 public static Method makeMethod() {
  Method meth = null;
 
  try {
   Class[] argTypes = new Class[] { int.class, String.class };
 
   meth = MethodAccessExampleWithArgs.class.getDeclaredMethod("bar",
     argTypes);
 
   meth.setAccessible(true);
  } catch (IllegalArgumentException e) {
   e.printStackTrace();
  } catch (NoSuchMethodException e) {
   e.printStackTrace();
  } catch (SecurityException e) {
   e.printStackTrace();
  }
 
  return meth;
 }
 
 // Using method handles
 public static MethodHandle makeMh() {
  MethodHandle mh;
 
  MethodType desc = MethodType.methodType(void.class, int.class,
    String.class);
 
  try {
   mh = MethodHandles.lookup().findVirtual(
     MethodAccessExampleWithArgs.class, "bar", desc);
   System.out.println("mh=" + mh);
  } catch (NoAccessException e) {
   throw (AssertionError) new AssertionError().initCause(e);
  }
  return mh;
 }
}

Following, is a class meant to test the two approaches of accessing the private method “bar” :

public class MethodAccessMain {
 
 private static void withReflectionArgs() {
  Method meth = MethodAccessExampleWithArgs.makeMethod();
 
  MethodAccessExampleWithArgs mh0 = new MethodAccessExampleWithArgs(0);
  MethodAccessExampleWithArgs mh1 = new MethodAccessExampleWithArgs(1);
 
  try {
   System.out.println("Invocation using Reflection");
   meth.invoke(mh0, 5, "Jabba the Hutt");
   meth.invoke(mh1, 7, "Boba Fett");
  } catch (IllegalAccessException e) {
   e.printStackTrace();
  } catch (IllegalArgumentException e) {
   e.printStackTrace();
  } catch (InvocationTargetException e) {
   e.printStackTrace();
  }
 }
 
 private static void withMhArgs() {
  MethodHandle mh = MethodAccessExampleWithArgs.makeMh();
 
  MethodAccessExampleWithArgs mh0 = new MethodAccessExampleWithArgs(0);
  MethodAccessExampleWithArgs mh1 = new MethodAccessExampleWithArgs(1);
 
  try {
   System.out.println("Invocation using Method Handle");
   mh.invokeExact(mh0, 42, "R2D2");
   mh.invokeExact(mh1, 43, "C3PO");
  } catch (Throwable e) {
   e.printStackTrace();
  }
 }
 
 public static void main(String[] args) {
  withReflectionArgs();
  withMhArgs();
 }
}

Related Article:

References :

Ilias Tsagklis

Ilias is a software developer turned online entrepreneur. He is co-founder and Executive Editor at Java Code Geeks.
Subscribe
Notify of
guest

This site uses Akismet to reduce spam. Learn how your comment data is processed.

0 Comments
Inline Feedbacks
View all comments
Back to top button