• 简单赋值语句的字节码


    java代码1:

    package com.bytecode;
    
    public class Wizard {
        private int age;
        
        public Wizard() {
            this.age = 100;
        }
    }

    javap -v Wizard.class 得到字节码:

    Classfile /D:/Users/Administrator/workspace/TestJava/bin/com/bytecode/Wizard.class
      Last modified 2018-3-14; size 311 bytes
      MD5 checksum 301ffac27f2fa331e20b98a912914551
      Compiled from "Wizard.java"
    public class com.bytecode.Wizard
      SourceFile: "Wizard.java"
      minor version: 0
      major version: 51
      flags: ACC_PUBLIC, ACC_SUPER
    
    Constant pool:
       #1 = Class              #2             //  com/bytecode/Wizard
       #2 = Utf8               com/bytecode/Wizard
       #3 = Class              #4             //  java/lang/Object
       #4 = Utf8               java/lang/Object
       #5 = Utf8               age
       #6 = Utf8               I
       #7 = Utf8               <init>
       #8 = Utf8               ()V
       #9 = Utf8               Code
      #10 = Methodref          #3.#11         //  java/lang/Object."<init>":()V
      #11 = NameAndType        #7:#8          //  "<init>":()V
      #12 = Fieldref           #1.#13         //  com/bytecode/Wizard.age:I
      #13 = NameAndType        #5:#6          //  age:I
      #14 = Utf8               LineNumberTable
      #15 = Utf8               LocalVariableTable
      #16 = Utf8               this
      #17 = Utf8               Lcom/bytecode/Wizard;
      #18 = Utf8               SourceFile
      #19 = Utf8               Wizard.java
    {
      public com.bytecode.Wizard();
        flags: ACC_PUBLIC
    
        Code:
          stack=2, locals=1, args_size=1
             0: aload_0       
             1: invokespecial #10                 // Method java/lang/Object."<init>":()V
             4: aload_0       
             5: bipush        100
             7: putfield      #12                 // Field age:I
            10: return        
          LineNumberTable:
            line 6: 0
            line 7: 4
            line 8: 10
          LocalVariableTable:
            Start  Length  Slot  Name   Signature
                0      11     0  this   Lcom/bytecode/Wizard;
    }

    在构造函数Wizard()中,局部变量表0处是this引用。

    指令 描述 操作数栈
    aload_0 this引用入操作数栈 this
    invokespecial #10 调用Object类的<init>方法,消耗栈中的this引用  
    aload_0 this引用再次推入操作数栈 this
    bipush 100 把整数100推入操作数栈 this, 100
    putfield  #12 调用this -> Wizard.age = 100,消耗栈中的this和100  

    java代码2:

    public class Wizard {
        private int age;
        private void grow() {
            this.age += 1;
        }
    }

    javap -v -p Wizard.class 得到字节码:

    Classfile /D:/Users/Administrator/workspace/TestJava/bin/com/bytecode/Wizard.class
      Last modified 2018-3-15; size 375 bytes
      MD5 checksum 1910939ad3f794132f14da4c1c417e96
      Compiled from "Wizard.java"
    public class com.bytecode.Wizard
      SourceFile: "Wizard.java"
      minor version: 0
      major version: 51
      flags: ACC_PUBLIC, ACC_SUPER
    
    Constant pool:
       #1 = Class              #2             //  com/bytecode/Wizard
       #2 = Utf8               com/bytecode/Wizard
       #3 = Class              #4             //  java/lang/Object
       #4 = Utf8               java/lang/Object
       #5 = Utf8               age
       #6 = Utf8               I
       #7 = Utf8               <init>
       #8 = Utf8               ()V
       #9 = Utf8               Code
      #10 = Methodref          #3.#11         //  java/lang/Object."<init>":()V
      #11 = NameAndType        #7:#8          //  "<init>":()V
      #12 = Utf8               LineNumberTable
      #13 = Utf8               LocalVariableTable
      #14 = Utf8               this
      #15 = Utf8               Lcom/bytecode/Wizard;
      #16 = Utf8               grow
      #17 = Fieldref           #1.#18         //  com/bytecode/Wizard.age:I
      #18 = NameAndType        #5:#6          //  age:I
      #19 = Utf8               SourceFile
      #20 = Utf8               Wizard.java
    {
      private int age;
        flags: ACC_PRIVATE
    
    
      public com.bytecode.Wizard();
        flags: ACC_PUBLIC
    
        Code:
          stack=1, locals=1, args_size=1
             0: aload_0       
             1: invokespecial #10                 // Method java/lang/Object."<init>":()V
             4: return        
          LineNumberTable:
            line 3: 0
          LocalVariableTable:
            Start  Length  Slot  Name   Signature
                0       5     0  this   Lcom/bytecode/Wizard;
    
      private void grow();
        flags: ACC_PRIVATE
    
        Code:
          stack=3, locals=1, args_size=1
             0: aload_0       
             1: dup           
             2: getfield      #17                 // Field age:I
             5: iconst_1      
             6: iadd          
             7: putfield      #17                 // Field age:I
            10: return        
          LineNumberTable:
            line 7: 0
            line 8: 10
          LocalVariableTable:
            Start  Length  Slot  Name   Signature
                0      11     0  this   Lcom/bytecode/Wizard;
    }

    关注grow方法:

    指令   描述 操作数栈
    aload_0 this入栈 this
    dup 栈顶的this复制一份,再入栈 this, this
    getfield #17 this出栈,this.age入栈 this, this.age
    iconst_1 常数1入栈 this, this.age, 1
    iadd 栈顶的2个值相加 this, (this.age + 1)
    putfield #17 给成员赋值,消耗两个栈元素  
  • 相关阅读:
    MVVM架构~knockoutjs实现简单的购物车
    Thrift架构~目录
    WebApi系列~在WebApi中实现Cors访问
    WebApi系列~基于RESTful标准的Web Api
    MVVM架构~目录
    IOS设计模式学习(20)命令
    MySQL保留关键字
    Eclipse with C++: "Launch failed. Binary not found."
    HTML5 Canvas鼠标与键盘事件
    通过openssh远程登录时的延迟问题解决
  • 原文地址:https://www.cnblogs.com/allenwas3/p/8545524.html
Copyright © 2020-2023  润新知