为什么Java反射调用比方法调用快?

为什么Java反射调用比方法调用快?,java,performance,reflection,execution,Java,Performance,Reflection,Execution,我发现了这个问题,并用我的应用程序进行了测试。 我正在调用和调用相同的方法 我尝试了不同的连续执行和不同的方法(加密、排序等),得到了以下结果 Executions|Invoke-Call ratio 1 | 62,78% 10 | 107,58% 100 | 76,74% 1000 | 80,01% 10000 | 116,88% 100000 | 82,80% 1000000 | 91,67% 我检查了是否

我发现了这个问题,并用我的应用程序进行了测试。 我正在调用和调用相同的方法

我尝试了不同的连续执行和不同的方法(加密、排序等),得到了以下结果

Executions|Invoke-Call ratio

1         | 62,78%

10        | 107,58%

100       | 76,74%

1000      | 80,01%

10000     | 116,88%

100000    | 82,80%

1000000   | 91,67%
我检查了是否可能使用了多个线程,但这不是我所能说的。 原因是什么

为了进一步澄清,请摘录我的基准: 调用部分:

Executable executable = new Executable();
Method execute = executable.getClass().getMethod("execute");
System.out.println("# Startup finished.");
for (float i = 0; i <= 6; i++)
{
    int executions = (int) Math.pow(10, i);
    long start = System.nanoTime();
    for (int j = 0; j <= executions - 1; j++)
    {
        execute.invoke(executable);
    }
    long stop = System.nanoTime();
    long delta = stop - start;
    System.out.println("Invoke;" + executions + ";" + delta);
}
System.out.println("# Shutdown finished.");
Executable Executable=新的可执行文件();
方法execute=execute.getClass().getMethod(“execute”);
System.out.println(“#启动完成”);

对于(float i=0;i仅为了感兴趣的人,代码按预期工作,调用速度比invoke快

# Startup finished.
Invoke  1   1683969
Invoke  10  1876447
Invoke  100 23376245
Invoke  1000    29035955
Invoke  10000   55816067
Invoke  100000  209290359
# Shutdown finished.
# Startup finished.
Call    1   64587
Call    10  18820
Call    100 209160
Call    1000    1656594
Call    10000   17318746
Call    100000  167565824
# Shutdown finished.

您可能测量错误(例如,JIT延迟)。向我们展示您的基准测试。正常调用通常要快得多,您应该展示您的代码。感谢您的评论,我已经从我的应用程序中提取了基准测试。
Executable.execute()
method看起来像什么?好的,我发现正如人们之前在他们的链接中建议的那样,您必须在两个单独的程序中执行调用和调用,否则会完全破坏结果。我现在得到了预期的结果。非常感谢。
public class Executable
{
    private int index = 0;
    private int testsize = 1111111;
    private byte[][] plain = new byte[testsize][];
    private byte[][] hashed = new byte[testsize][];
    private SecureRandom securerandom;
    private MessageDigest messagedigest;

    public Executable()
    {
        this.securerandom = new SecureRandom();
        this.messagedigest = MessageDigest.getInstance("SHA-256");
        for (int i = 0; i <= testsize - 1; i++)
        {
            this.plain[i] = new byte[8];
            this.securerandom.nextBytes(this.plain[i]);
        }
    }

    public void execute()
    {
        messagedigest.update(this.plain[index]);
        this.hashed[index] = messagedigest.digest();
        index++;
    }
}
# Startup finished.
Invoke  1   1683969
Invoke  10  1876447
Invoke  100 23376245
Invoke  1000    29035955
Invoke  10000   55816067
Invoke  100000  209290359
# Shutdown finished.
# Startup finished.
Call    1   64587
Call    10  18820
Call    100 209160
Call    1000    1656594
Call    10000   17318746
Call    100000  167565824
# Shutdown finished.