実行中のメソッドの名前を取得するにはどうすればよいですか?

1。概要

実行されている現在のJavaメソッドの名前を知る必要がある場合があります。

この簡単な記事では、現在の実行スタックでメソッド名を取得する簡単な方法をいくつか紹介します。

2. Java 9:スタックウォーキングAPI

Java 9では、JVMスタックフレームを遅延的かつ効率的にトラバースするためのStack-WalkingAPIが導入されました。このAPIで現在実行中のメソッドを見つけるために、簡単なテストを作成できます。

public void givenJava9_whenWalkingTheStack_thenFindMethod() { StackWalker walker = StackWalker.getInstance(); Optional methodName = walker.walk(frames -> frames .findFirst() .map(StackWalker.StackFrame::getMethodName)); assertTrue(methodName.isPresent()); assertEquals("givenJava9_whenWalkingTheStack_thenFindMethod", methodName.get()); }

まず、getInstance()ファクトリメソッドを使用してStackWalkerインスタンスを取得します。次に、walk()メソッドを使用して、スタックフレームを上から下にトラバースします。

  • 徒歩()メソッドは、スタックフレームのストリームに変換することができます-ストリームを 何にでも
  • 指定されたストリームの最初の要素は、スタックの一番上のフレームです
  • スタックの一番上のフレームは常に現在実行中のメソッドを表します

したがって、ストリームから最初の要素を取得すると、現在実行中のメソッドの詳細がわかります。具体的には、StackFrame.getMethodName()使用してメソッド名を見つけることができます。

2.1。利点

他のアプローチ(後で詳しく説明します)と比較すると、Stack-WalkingAPIにはいくつかの利点があります。

  • ダミーの匿名内部クラスインスタンスを作成する必要はありません— new Object()。getClass(){}
  • ダミーの例外を作成する必要はありません— new Throwable()
  • コストがかかる可能性があるスタックトレース全体を熱心にキャプチャする必要はありません

それどころか、StackWalkerはスタックを1つずつ怠惰に歩くだけです。この場合、すべてのフレームを熱心にキャプチャするスタックトレースアプローチとは対照的に、トップフレームのみをフェッチします。

つまり、Java 9以降を使用している場合は、Stack-WalkingAPIを使用してください。

3.getEnclosingMethodの使用

getEnclosingMethod() APIを使用して、実行されているメソッドの名前を見つけることができます。

public void givenObject_whenGetEnclosingMethod_thenFindMethod() { String methodName = new Object() {} .getClass() .getEnclosingMethod() .getName(); assertEquals("givenObject_whenGetEnclosingMethod_thenFindMethod", methodName); }

4.スロー可能なスタックトレースの使用

Throwableスタックトレースを使用すると、現在実行されているメソッドのスタックトレースが得られます。

public void givenThrowable_whenGetStacktrace_thenFindMethod() { StackTraceElement[] stackTrace = new Throwable().getStackTrace(); assertEquals( "givenThrowable_whenGetStacktrace_thenFindMethod", stackTrace[0].getMethodName()); }

5.スレッドスタックトレースの使用

また、現在のスレッドのスタックトレース(JDK 1.5以降)には、通常、実行されているメソッドの名前が含まれています。

public void givenCurrentThread_whenGetStackTrace_thenFindMethod() { StackTraceElement[] stackTrace = Thread.currentThread() .getStackTrace(); assertEquals( "givenCurrentThread_whenGetStackTrace_thenFindMethod", stackTrace[1].getMethodName()); }

ただし、このソリューションには1つの重大な欠点があることを覚えておく必要があります。一部の仮想マシンは、1つ以上のスタックフレームをスキップする場合があります。これは一般的ではありませんが、これが発生する可能性があることに注意する必要があります。

6.結論

このチュートリアルでは、現在実行されているメソッドの名前を取得する方法の例をいくつか示しました。例は、スタックトレースとgetEnclosingMethod()に基づいています。

いつものように、GitHubでこの記事に記載されている例を確認できます。また、Java 9の例は、Java 9GitHubモジュールで利用できます。