zoukankan      html  css  js  c++  java
  • 对象

    这块内容面试官一般会问,面试的难易程度也不一样,有些面试官或许让你讲讲虚拟机的内存模型即可,

    有些也会让你解释垃圾回收的实现,当然也会有虚拟机调优的实战经验,线上问题排查等等。

    场景对话:面试官:你对java的对象熟悉吗?

    我:(对象?他应该会问一些关于对象初始化以及回收的东西吧)  嗯,略微了解(俗话说凡事不能说太满,容易被打脸)

    面试官:你知道怎么创建一个对象吗?

    我:1 new  2利用反射建立 3使用clone()方法 4反序列化  

    面试官:你能简单说说对象的创立过程吗?

    我:[检测类是否被加载]虚拟机遇到创建对象的指令时,先去检查这个指令的参数能否在常量池中定位到一个类的符号引用,并检查这个符号代表的类是否完成了类加载的过程,若无必须先执行对应的类加载。

    [为对象分配内存]在类加载检查通过后,虚拟机就开始为对象分配内存,此时所需内存的大小就已经确定了。只需要在堆上分配所需要的内存即可。

    [对非配的内存空间初始化零值]对象的内存分配完成后,还需要将对象的内存空间都初始化为零值,这样能保证对象即使没有赋初值,也可以直接使用。

    [设置对象头信息]分配完内存空间,初始化零值之后,虚拟机还需要对对象进行其他必要的设置,设置的地方都在对象头中,包括这个对象所属的类,类的元数据信息,对象的hashcode,GC分代年龄等信息。

    [执行init方法]执行完上面的步骤之后,在虚拟机里这个对象就算创建成功了,但是对于Java程序来说还需要执行init方法才算真正的创建完成,因为这个时候对象只是被初始化零值了,还没有真正的去根据程序中的代码分配初始值,调用了init方法之后,这个对象才真正能使用。

    面试官:分配内存的方法你能具体说一下吗?

    我:分配方法分为两种情况吧。 

       当堆中内存是绝对规整时,采用“指针碰撞”的方法,所有用过的内存放在一边,空闲的内存放在另一边,中间放一个指针作为分界点的指示器,将对象放在空闲内存区,然后指针移动相应的位置。

       当堆中内存不规整时,这时候虚拟机需要维护一个列表,来记录哪些内存是可用的。分配内存的时候需要找到一个可用的内存空间,然后在列表上记录下已被分配,这种方式成为空闲列表。

    面试官:你知道对象的创建是非常频繁的,并发情况下怎么解决线程安全的呢?

    我:(emmm.....这个以前看过啊,太久远了%……&努力回想)哦,对了。 

    对于指针碰撞虚拟机是采用CAS来保证操作的原子性的。 第二种是在堆中为每一个线程分配一个[本地线程分配缓冲](Thread Local Allocation Buffer TLAB),哪个线程要分配空间就在哪个TLAB上分配。

    只有TLAB内存用完并分配新的TLAB时才需要同步锁定,可以通过-XX+/UseTLAB参数来设置是否使TLAB 

    面试官:了解得蛮详细的,你刚才说设置对象的头部信息,都包含些什么信息呢? 

    我:(沃日,这有完没完....)HotSpot虚拟机的对象布局为对象头,实例数据,对齐填充(顺便把内存布局说了一下)。对象头包括:[Mark Word]存储对象的运行数据包括哈希码,GC分代年龄,锁状态标志等。另一部分存储指向方法区对象类型的指针,如果是数组对象的话,还有额外一部分用于存储数组长度。

    面试官:你应该知道java程序是通过站上面的对象引用来操作堆上面具体的对象的,那引用是如何通过访问定位到对象的呢? 

    我:现在比较主流的方法是使用句柄和直接指针的方式,如下:

     

    HotSpot是采用的第二种直接指针的方式。

    比较这两种方式的话,他们的优点: 第一种:在垃圾回收过程中对象移动是非常普遍的,栈中存储的引用可以不变,只需要改变句柄中的指针。第二种速度快并且节省空间。

    面试官:okok,你了解GC么?

    我:(暂时先写到这里,先去打游戏了,今晚是战斗之夜....)

  • 相关阅读:
    C# ListView应用
    C# 使用System.Speech 进行语音播报和识别
    支付宝支付-扫码支付详解
    使用git提交项目到码云
    C# byte[]数组和string的互相转化 (四种方法)
    C#中字节数组byte[]、图片image、流stream,字符串string、内存流MemoryStream、文件file,之间的转换
    C# 结构体和List<T>类型数据转Json数据保存和读取
    对 JSON 数据进行序列化和反序列化
    win10与虚拟机fedora14使用samba文件共享
    serialVersionUID, ObjectInputStream与ObjectOutputStream类,Serializable接口,serialVersionUID的作用和用法
  • 原文地址:https://www.cnblogs.com/WegYcx/p/7498954.html
Copyright © 2011-2022 走看看