美文网首页
JAVA运行时—内存分配情况

JAVA运行时—内存分配情况

作者: 远o_O | 来源:发表于2017-05-23 14:38 被阅读29次

    对象的内存布局

    • 在HotSpot虚拟机中,对象在内存中存储的布局可以分为3块区域:对象头(Header)、实例数据(Instance Data)、对齐填充(Padding)。
      • 对象头包括两部分信息:
        • 第一部分用于存储对象的自身的运行时数据,如哈希码(HashCode)、GC分代年龄、锁状态标志、线程持有的锁、偏向线程ID等。
      • 第二部分是类型指针,即对象指向它的类元数据(存放在方法区)的指针,虚拟机通过这个指针来确定这个对象是哪个类的实例。
    • 实例数据部分:是对象真正存储的有效信息,也是在程序代码中所定义的各种类型的字段内容。无论是从父类继承下来的,还是在子类中定义的,都需要记录起来。
    • 对齐填充:略。

    对象的访问定位

    概述:建立对象是为了使用对象,我们的Java程序需要通过栈上的reference数据来操作堆上的具体对象。目前主流的访问方式有使用句柄直接指针两种。

    • 直接指针访问方式的最大好处就是速度更快,它节省了一次指针定位的时间开销,由于对象的访问在Java中非常频繁,HotSpot采用的便是这种方式。
    • 下图即为Java利用直接指针访问对象:
    Paste_Image.png

    实例分析###

    public class Dog{
        private int age;
        
        public Dog() {
        }
        
        public Dog(int age){
            this.age = age;
        }
        
        public int getAge() {
            return age;
        }
        
        public static void main(String[] args)  {
            Dog dog = new Dog();
            ...
        }
    }
    
    • 内存分配图如下
    Paste_Image.png
    • 重点内容说明
    • 构造方法or实例方法:需要将this指针(即对象地址),传递进方法内,才可以访问属性,即才知道访问哪一个对象的属性。这才是方法内为什么会隐含一个this指针。
    • 静态方法:由于静态方法内不允许含有对象属性,因此应该不含有this指针。这和构造方法是不同的,我也一直对《Thinking in Java》所提到的:“构造方法应该隐含是静态的”,持有疑问态度,虽然某些角度看,两者有相似的地方,但是从大部分方面看都是不同的。
    • 调用构造方法不一定会创建对象,但是调用构造方法可以初始化对象。最强有力的证明就是new子类对象的时候肯定会调用父类对象的构造方法,但是并不会创建父类对象。虚拟机只有接收到new指令的时候,才会真正的去创建父类对象。

    好了,最后打住收工,啊弥陀否!!!

    相关文章

      网友评论

          本文标题:JAVA运行时—内存分配情况

          本文链接:https://www.haomeiwen.com/subject/hcgwxxtx.html