Invoke.java
package com.alibaba.fastjson2.benchmark.fastcode;
import com.alibaba.fastjson2.util.JDKUtils;
import org.openjdk.jmh.annotations.Benchmark;
import org.openjdk.jmh.annotations.Mode;
import org.openjdk.jmh.infra.Blackhole;
import org.openjdk.jmh.runner.Runner;
import org.openjdk.jmh.runner.RunnerException;
import org.openjdk.jmh.runner.options.Options;
import org.openjdk.jmh.runner.options.OptionsBuilder;
import java.lang.invoke.*;
import java.lang.reflect.Method;
import java.util.concurrent.TimeUnit;
import java.util.function.ObjIntConsumer;
public class Invoke {
static final Method METHOD_SET_ID;
static final ObjIntConsumer FUNC_SET_ID;
static final Object OBJECT;
static int value = 12345;
static {
Method method = null;
try {
method = Bean.class.getMethod("setId", int.class);
} catch (Exception e) {
e.printStackTrace();
}
METHOD_SET_ID = method;
ObjIntConsumer function = null;
try {
MethodHandles.Lookup lookup = JDKUtils.trustedLookup(Bean.class);
MethodType invokedType = MethodType.methodType(ObjIntConsumer.class);
MethodHandle target = lookup.findVirtual(Bean.class, "setId", MethodType.methodType(void.class, int.class));
MethodType instantiatedMethodType = MethodType.methodType(void.class, Bean.class, int.class);
MethodType samMethodType = MethodType.methodType(void.class, Object.class, int.class);
CallSite callSite = LambdaMetafactory.metafactory(
lookup,
"accept",
invokedType,
samMethodType,
target,
instantiatedMethodType
);
function = (ObjIntConsumer) callSite.getTarget().invoke();
} catch (Throwable e) {
e.printStackTrace();
}
FUNC_SET_ID = function;
Bean bean = new Bean();
bean.id = 1234;
bean.name = "DataWorks";
OBJECT = bean;
}
@Benchmark
public void reflect(Blackhole bh) throws Exception {
Object obj = OBJECT;
METHOD_SET_ID.invoke(obj, value);
bh.consume(obj);
}
@Benchmark
public void direct(Blackhole bh) throws Exception {
Bean obj = (Bean) OBJECT;
obj.setId(value);
bh.consume(obj);
}
@Benchmark
public void lambda(Blackhole bh) throws Exception {
Object obj = OBJECT;
FUNC_SET_ID.accept(obj, value);
bh.consume(obj);
}
public static class Bean {
private int id;
private String name;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
public static void main(String[] args) throws RunnerException {
Options options = new OptionsBuilder()
.include(Invoke.class.getName())
.include(InvokeFirst.class.getName())
.mode(Mode.Throughput)
.timeUnit(TimeUnit.MILLISECONDS)
.warmupIterations(1)
.forks(1)
.build();
new Runner(options).run();
}
}