Jak uzyskać bieżące śledzenie stosu w Javie, na przykład jak w .NET możesz to zrobić Environment.StackTrace
?
Znalazłem, Thread.dumpStack()
ale nie tego chcę - chcę odzyskać ślad stosu, a nie go wydrukować.
stack-trace
java
ripper234
źródło
źródło
Odpowiedzi:
Możesz użyć
Thread.currentThread().getStackTrace()
.Zwraca tablicę
StackTraceElement
s reprezentującą bieżący ślad stosu programu.źródło
String fullStackTrace = org.apache.commons.lang.exception.ExceptionUtils.getFullStackTrace(e);
stackoverflow.com/a/10620951/11236new Throwable().getStackTrace()
jest znacznie szybszy, ponieważ nie musi sprawdzaćthis != Thread.currentThread()
i omija potencjalnych obciążeń JVM związanych z wywoływaniem go przez child-class (Exception extends Throwable
)jest w porządku, jeśli nie obchodzi cię, jaki jest pierwszy element stosu.
będzie miał zdefiniowaną pozycję dla twojej obecnej metody, jeśli to ma znaczenie.
źródło
(new Throwable()).getStackTrace()
jest także szybszy w wykonywaniu (patrz bugs.sun.com/bugdatabase/view_bug.do?bug_id=6375302 )(new Exception()).getStackTrace()
gdy żądany ślad stosu znajduje się w bieżącym wątku (co zawsze będzie miało miejsceThread.currentThread().getStackTrace();
źródło
new Exception().printStackTrace(System.out)
co pamiętam, pętla for prawdopodobnie ma mniejszy narzut, ale i tak powinieneś używać jej tylko jako funkcji debugowania ...for (StackTraceElement ste : Thread.currentThread().getStackTrace()) { if(ste.toString().contains("mypackages")){ System.out.println(ste); } }
jest dostępna od wersji JDK1.5.
W przypadku starszej wersji możesz przekierować
exception.printStackTrace()
doStringWriter()
:źródło
new Throwable().getStackTrace()
jest dostępna od JDK1.4…Możesz użyć do tego wspólnego Apache:
źródło
org.apache.commons.lang3
, pełna linia to:org.apache.commons.lang3.exception.ExceptionUtils.getStackTrace(e);
org.apache.commons.lang3
, który początkowo przeoczyłem - import używalang3
zamiastlang
i zastępujegetFullStackTrace
gogetStackTrace
.ExceptionUtils.getStackTrace(new Throwable())
wyrażenia, aby uzyskać ślad stosu.Na Androidzie znacznie łatwiejszym sposobem jest użycie tego:
źródło
Aby uzyskać ślad stosu wszystkich wątków, możesz albo użyć narzędzia jstack, JConsole, albo wysłać sygnał zabicia-wyjścia (w systemie operacyjnym Posix).
Jeśli jednak chcesz to zrobić programowo, możesz spróbować użyć ThreadMXBean:
Jak wspomniano, jeśli chcesz tylko śledzenia stosu bieżącego wątku, jest to o wiele łatwiejsze - wystarczy użyć
Thread.currentThread().getStackTrace()
;źródło
System.err.println(elems[i])
na każdym z nich). Druga linia fragmentu kodu jest krótkabean.
przed,dumpAllThreads
ale myślę, że większość ludzi może to rozwiązać.Inne rozwiązanie (tylko
3531 znaków):źródło
Głupie ja, to jest
Thread.currentThread().getStackTrace();
źródło
Tony, jako komentarz do zaakceptowanej odpowiedzi, udzielił najlepszej odpowiedzi, która faktycznie odpowiada na pytanie PO :
... OP NIE zapytał, jak uzyskać
String
ślad stosu z plikuException
. I chociaż jestem wielkim fanem Apache Commons, kiedy jest coś tak prostego jak powyższe, nie ma logicznego powodu, aby korzystać z zewnętrznej biblioteki.źródło
Thread.getAllStackTraces()
co daje ciMap<Thread, StackTraceElement[]>
. Hotspot zabezpiecza wszystkie wątki, ilekroć będzie to potrzebne. Zing może przenosić pojedyncze wątki do bezpiecznego punktu, nie przeszkadzając innym. Zdobycie stacktrace wymaga bezpiecznego punktu.Thread.getAllStackTraces()
pobiera wszystkie ślady stosu i zatrzymuje wszystkie wątki tylko raz. Oczywiście musisz dowiedzieć się, które mapowanie Cię interesuje.sugeruję to
jest prostszym sposobem i ma tę zaletę, że nie tworzy wyjątku ani nie można go rzucać, gdy może nie być żadnego problemu, i jest znacznie bardziej istotny.
źródło
new Exception("Stack trace").printStackTrace();
tak naprawdę buduje ThrowablePobieranie stacktrace:
Drukowanie stacktrace (JAVA 8+):
Drukowanie stacktrage (JAVA 7):
źródło
W Javie 9 istnieje nowy sposób:
źródło
Mam metodę narzędzia, która zwraca ciąg znaków z stacktrace:
I po prostu loguj jak ...
źródło
java.util.logging.Logger#log(Level, String, Throwable)
już to robi. Jest to niepotrzebne przepisywanie rzeczy, które już istnieją w standardowej bibliotece Java, i wskazuje nowym programistom w złym kierunku, który jest z dala od dokumentacji. Robiąc to teraz, wymusiłeś sformatowanie Stacktrace w określony sposób, gdzie jakologging
API pozwala na dynamiczne zmienianie formatowania instrukcji dziennika podczas jej określania. O ile mi wiadomo,log4j
ma również podobne zachowanie. Nie wymyślaj na nowo koła, bo w końcu tracisz rzeczy, które wyjaśniłem.Throwable
od doHandler
s przez doFormatter
S w 2012 roku, który był Java7, bardziej niż ja tutaj wymienione A funkcje te sięgają znacznie dłużej niż Java7 została wokół;. Stąd J2SE 5.0 Javadocs)Aby sznurować za pomocą guawy:
źródło
lub
źródło
Może mógłbyś spróbować:
Ciąg „errorDetail” zawiera ślad stosu.
źródło
wykonaj pętlę przez StackTraceElement i uzyskaj pożądany wynik.
źródło
Użyłem odpowiedzi z góry i dodałem formatowanie
źródło
Możesz użyć narzędzia jstack, jeśli chcesz sprawdzić bieżący stos wywołań swojego procesu.
źródło
To jest stary post, ale oto moje rozwiązanie:
Więcej informacji i więcej metod: http://javarevisited.blogspot.fr/2013/04/how-to-get-current-stack-trace-in-java-thread.html
źródło
Thread.dumpStack()
bezpośrednio, ponieważ jest to metoda statyczna.System.out.println(Arrays.toString(Thread.currentThread().getStackTrace()));
Pomoże to wydrukować ślad stosu bez pętli.
źródło