Kiedy czytałem kod bajtowy jvm, z jakiejś małej funkcji java odkryłem, że kiedy nowa zmienna lokalna jest kaculated na stosie operandów, zakładając, że będzie przechowywana w tabeli zmiennych lokalnych, ale zwykle będzie załadowana do operandu stos natychmiast (tylko w sensie kodu bajtowego dosłownie). Nie rozumiem dobrze operacji, czy to niepotrzebna operacja?Dlaczego kod bajtowy java "zapisz" często następuje po "załadowaniu"?
Odpowiedz
Kompilator Javy ma tendencję do kompilowania rzeczy w bardzo prosty i bezpośredni sposób, pozostawiając optymalizację JIT.
Na przykład, jeśli piszesz x *= 3; x *= 4;
, prawdopodobnie będziesz dostać kodu bajtowego wzdłuż linii
iload_1
iconst_3
imul
istore_1
iload_1
iconst_4
imul
istore_1
Kompilator może teoretycznie dowiedzieć się, że para sklep/obciążenie jest zbędny i wyjąć go. Ale jest kilka powodów, aby tego nie robić - 1) to dodaje wiele komplikacji, bez żadnej korzyści, ponieważ JIT i tak optymalizuje wszystko 2) powoduje, że debugowanie jest trudniejsze, ponieważ nie masz już dostępu do wartości wszystkich zmiennych lokalnych 3) jeśli wyjątek zostanie w jakiś sposób wyrzucony w środku tego wyrażenia, zmienne lokalne będą miały niepoprawne wartości.
Patrząc na dspin
kodu binarnego
Method void dspin()
0 dconst_0 // Push double constant 0.0
1 dstore_1 // Store into local variables 1 and 2
2 goto 9 // First time through don't increment
5 dload_1 // Push local variables 1 and 2
6 dconst_1 // Push double constant 1.0
7 dadd // Add; there is no dinc instruction
8 dstore_1 // Store result in local variables 1 and 2
9 dload_1 // Push local variables 1 and 2
10 ldc2_w #4 // Push double constant 100.0
13 dcmpg // There is no if_dcmplt instruction
14 iflt 5 // Compare and loop if less than (i < 100.0)
17 return // Return void when done
The tylko load
który następuje store
jest przesunięcie 9. Można zauważyć, że przesunięcie 9 można osiągnąć w dwóch różnych dróg: (1) od przesunięcie 2 z goto 9
; oraz (2) kolejno z przesunięciem 8
dload_1
popycha wartości zmiennych lokalnych 1 i 2 na stosie argumentu (dwie zmienne ze względu double
): w przypadku (1), gdy próbuje wejść do pętli po raz pierwszy, oraz w przypadku (2) przy próbie wejścia do pętli w późniejszych punktach czasowych.
Co ciekawe, w tym przykładzie zachowanie wszystkich store
i load
zachowań programu nie zmieni się. Jednak kompilator Java zwykle nie stara się być inteligentny. Kompiluje kod Java mniej lub bardziej bezpośrednio. W tym przypadku lokalna zmienna i
bezpośrednio odpowiada zmiennym lokalnym 1 i 2.
Aby uzyskać więcej informacji, patrz Optimization by Java Compiler.
Jeśli usunę wszystkie 'store' i' load', czy powyższy kod nadal będzie działał? –
@ Q_SJ, zapoznaj się z edytowaną odpowiedzią. – dejvuth
Jeśli dobrze cię rozumiem, masz na myśli, że w pewnej sytuacji javac naprawdę generuje dziwną parę 'store' i' load'. Czy mam rację? –
- 1. Demontaż Java JIT skompilowany natywny kod bajtowy
- 2. Dlaczego setuptools muszą pisać kod bajtowy?
- 3. GHC Core jako "kod bajtowy"?
- 4. Jak sprawdzić kod bajtowy Pythona?
- 5. Jak sprawdzić kod bajtowy java wygenerowany przez Clojure z rep?
- 6. Kod bajtowy wykrywający język Python
- 7. Jak emitować i wykonywać kod bajtowy Java w czasie wykonywania?
- 8. Czy dynamicznie generowany kod bajtowy java wymaga jakiejkolwiek optymalizacji?
- 9. Sprawdź, czy kod bajtowy Java zawiera symbole debugowania
- 10. Dlaczego zaćmienie zawsze następuje po @param myParameter w JavaDoc?
- 11. Gdzie status wyjścia następuje po pułapce/zwrocie?
- 12. powolny kod bajtowy z ogona rekurencji
- 13. Czy cały kod bajtowy skompilowany ze źródeł java może zostać zdekompilowany do źródeł java?
- 14. Angularowe ładowanie po załadowaniu html
- 15. pycurl/curl nie następuje po opcji CURLOPT_TIMEOUT
- 16. Zdarzenie wyzwalające po załadowaniu jQuery
- 17. Skompiluj kod lua, przechowuj kod bajtowy, a następnie załaduj i uruchom go
- 18. Dlaczego Java jest często używana w aplikacjach korporacyjnych?
- 19. Zinterpretować coś i uruchomić wygenerowany kod bajtowy w Javie?
- 20. ścieżka biblioteki po załadowaniu dynamicznym?
- 21. Funkcja wywołania jQuery po załadowaniu
- 22. działa funkcja po załadowaniu strony
- 23. Po uruchomieniu kodu po załadowaniu Railsa?
- 24. Dlaczego standardy często są zamknięte?
- 25. Co oznacza pozbawiony JAR (nie kod bajtowy dla metod)?
- 26. Czy jest jakiś sposób programowo wygenerować kod bajtowy Pythona?
- 27. Jak ustawić kod bajtowy Kotlina w projekcie Gradle na Java 8?
- 28. jcrop zmienia obraz po załadowaniu strony
- 29. Dlaczego próbki jQuery często pomijają typ skryptu?
- 30. Sprawdzanie poprawności sprawdzania poprawności natychmiast po załadowaniu
Przykład proszę. Trudno powiedzieć, o czym mówisz inaczej. Niemożliwe, naprawdę. – EJP
Rozwiąż swoje pytanie, proszę. –
Nie można w zadowalającym stopniu odpowiedzieć na to pytanie w komentarzu. Edytuj go na swoje pytanie, gdzie powinno być na pierwszym miejscu. – EJP