3 回答
TA贡献1887条经验 获得超5个赞
您可以生成堆栈跟踪并使用StackTraceElements中的信息。
例如,实用程序类可以为您返回调用类名称:
public class KDebug {
public static String getCallerClassName() {
StackTraceElement[] stElements = Thread.currentThread().getStackTrace();
for (int i=1; i<stElements.length; i++) {
StackTraceElement ste = stElements[i];
if (!ste.getClassName().equals(KDebug.class.getName()) && ste.getClassName().indexOf("java.lang.Thread")!=0) {
return ste.getClassName();
}
}
return null;
}
}
如果你调用KDebug.getCallerClassName()从bar(),你会得到"foo"。
现在假设您想知道方法调用的类bar(这会更有趣,也许您真正想要的是)。您可以使用以下方法:
public static String getCallerCallerClassName() {
StackTraceElement[] stElements = Thread.currentThread().getStackTrace();
String callerClassName = null;
for (int i=1; i<stElements.length; i++) {
StackTraceElement ste = stElements[i];
if (!ste.getClassName().equals(KDebug.class.getName())&& ste.getClassName().indexOf("java.lang.Thread")!=0) {
if (callerClassName==null) {
callerClassName = ste.getClassName();
} else if (!callerClassName.equals(ste.getClassName())) {
return ste.getClassName();
}
}
}
return null;
}
那是用于调试吗?如果没有,可能有一个更好的解决方案。
TA贡献1963条经验 获得超6个赞
要获得呼叫者/被呼叫者的类名,请使用以下代码,它对我来说很好用。
String callerClassName = new Exception().getStackTrace()[1].getClassName();
String calleeClassName = new Exception().getStackTrace()[0].getClassName();
TA贡献2012条经验 获得超12个赞
堆栈跟踪
这高度取决于您要查找的内容...但是,这应该直接在此对象中获得调用此方法的类和方法。
索引0 =线程
索引1 =这个
索引2 =直接呼叫者,可以是自己。
索引3 ... n =相互调用以获得索引2及以下的类和方法。
对于类/方法/文件名:
Thread.currentThread().getStackTrace()[2].getClassName();
Thread.currentThread().getStackTrace()[2].getMethodName();
Thread.currentThread().getStackTrace()[2].getFileName();
上课:
Class.forName(Thread.currentThread().getStackTrace()[2].getClassName())
仅供参考:Class.forName()抛出不是运行时的ClassNotFoundException。您需要尝试抓住。
同样,如果您希望忽略类本身内的调用,则必须添加一些带有逻辑的循环来检查该特定事物。
像...(我没有测试过这段代码,所以要当心)
StackTraceElement[] stes = Thread.currentThread().getStackTrace();
for(int i=2;i<stes.length;i++)
if(!stes[i].getClassName().equals(this.getClass().getName()))
return stes[i].getClassName();
StackWalker
StackWalker StackFrame
请注意,这不是详尽的指南,而是这种可能性的一个示例。
打印每个StackFrame的Class(通过获取Class引用)
StackWalker.getInstance(Option.RETAIN_CLASS_REFERENCE)
.forEach(frame -> System.out.println(frame.getDeclaringClass()));
做同样的事情,但首先将流收集到一个列表中。仅用于演示目的。
StackWalker.getInstance(Option.RETAIN_CLASS_REFERENCE)
.walk(stream -> stream.collect(Collectors.toList()))
.forEach(frame -> System.out.println(frame.getDeclaringClass()));
添加回答
举报