• JVM之Class文件


    1、JVM之class


    工作好几年了,但是对jdk底层、JVM原理方面很多东西都是一知半解,现在打算单独找一大快时间来弥补一下这方面的知识,带着讨论式的学习方式。一起探索 JVM 底层吧

    众所周知 Java 特性:一次编译到处运行(跨平台)

    跨平台的能力就是 Java 虚拟机 JVM 实现的,JDK中到底有哪些东西呢?如下图!

    在图中最下面这个地方 Java HotSpot VM 就是我们常说的 JVM 虚拟机,JVM 由什么组成呢?

    既然当我们清楚JVM的组成部分后,那当一段程序执行时,JVM到底是怎么做的,又如何去印证这一说法呢?

    package com.liuyuncen.jvm;
    
    public class Main {
        public static void main(String[] args) {
            Main m = new Main();
            int function = m.function();
        }
    
        public int function(){
            int a = 1;
            int b = 2;
            int c = ( a + b ) * 10;
            return c;
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15

    1.1、反编译 class 文件

    当我们有如上一段程序后,我们通过 javac 命令可以得到一个 .class 的文件

    这里我直接用的 IDEA 工具,编译后在 target 路径下看到的 .class 文件

    当我们用记事本打开这个 Main.class 文件后,我们会看到一大堆字节码

    这其实就印证了之前我们所说的,JAVA特性,一次编译到处运行,JVM.java 文件编译成 .class 文件后,最终由计算机运行,而计算机就是去读这样的二进制字符,我们看到的是十六进制,大同小异。

    进制编码是给计算机看的,而不是给我们看的,虽然我们也可以通查阅 Oracle 的官方文档找到每个字符对应的含义,但是这样查询未免也… 太爽了吧,所以 Oracle 提供了另外一个工具 javap

    1.2、Javap 反编译工具

    通过 javap 反编译 class 文件获得 txt 文件

    javap -c Main.class > math.txt
    
    • 1

    我们可以得到这样一个文本

    Compiled from "Main.java"
    public class com.liuyuncen.jvm.Main {
      public com.liuyuncen.jvm.Main();
        Code:
           0: aload_0
           1: invokespecial #1                  // Method java/lang/Object."":()V
           4: return
    
      public static void main(java.lang.String[]);
        Code:
           0: new           #2                  // class com/liuyuncen/jvm/Main
           3: dup
           4: invokespecial #3                  // Method "":()V
           7: astore_1
           8: aload_1
           9: invokevirtual #4                  // Method function:()I
          12: istore_2
          13: return
    
      public int function();
        Code:
           0: iconst_1
           1: istore_1
           2: iconst_2
           3: istore_2
           4: iload_1
           5: iload_2
           6: iadd
           7: bipush        10
           9: imul
          10: istore_3
          11: iload_3
          12: ireturn
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34

    我们可以大体看出一些东西来!但是具体的一些指令什么的,看不懂。没关系,我们可以去查官网,查资料

    就拿 iconst_1 而言,表示将 int 类型常量 1 压入栈中

    • istore_1 将 int 类型值存入局部变量 1
    • iconst_2 将 int 类型常量 2 压入栈中
    • istore_2 将 int 类型值存入局部变量2

    _1_2 代表什么呢?其实就是代表类中的局部变量,你先初始化一个 a 那 a 就占用了第1个下标,再初始化了 b 那 b 就占用了第2个下标。紧接着就是 _3 _4…其实还有 _00 代表的 this 类本身

    所以这就解释的通了,人们通过写 main 方法等各个函数后,再运行 main 方法,先通过 javac 编译成 class 文件,而计算机就是通过这些指令集去运行程序。

  • 相关阅读:
    甲氨蝶呤修饰PEG-PLGA纳米粒MTX-PLGA|载紫杉醇PTX的PLGA纳米粒PLGA-SS-PTX(定制)
    10.25verilog复习,代码规范复盘,触发器复习
    MySQL索引
    1.6 线程池原理与实战
    一天撸一个财务APP系统【安卓端+前端+后端】
    BUUCTF msic 专题(128)[ACTF新生赛2020]剑龙
    Ubuntu16.04安装网卡驱动
    BreederDAO 第一项提案发布:DAO 组织的宪法章程
    利用vue-cli构建SPA项目以及在SPA项目中使用路由
    scrapy+scrapyd+gerapy 爬虫调度框架
  • 原文地址:https://blog.csdn.net/qq_39550368/article/details/126192839