• Java虚拟机


    JVM内存模型:

    线程私有的运行时数据区: 程序计数器、Java 虚拟机栈、本地方法栈。

    线程共享的运行时数据区:Java 堆、方法区。

     

    (1)程序计数器:

    程序计数器表示当前线程所执行的字节码的行号指示器。

    程序计数器不会产生StackOverflowError和OutOfMemoryError。

    (2)虚拟机栈:

    Java 虚拟机栈用来描述 Java 方法执行的内存模型。线程创建时就会分配一个栈空间,线程结束后栈空间被回收。

    栈中元素用于支持虚拟机进行方法调用,每个方法在执行时都会创建一个栈帧存储方法的局部变量表、操作栈、动态链接和返回地址等信息。

    虚拟机栈会产生两类异常:

    StackOverflowError:线程请求的栈深度大于虚拟机允许的深度抛出。

    OutOfMemoryError:如果 JVM 栈容量可以动态扩展,虚拟机栈占用内存超出抛出。

    (3)本地方法栈:

    本地方法栈与虚拟机栈作用相似,不同的是虚拟机栈为虚拟机执行 Java 方法服务,本地方法栈为本地方法服务。可以将虚拟机栈看作普通的java函数对应的内存模型,本地方法栈看作由native关键词修饰的函数对应的内存模型。

    本地方法栈会产生两类异常:

    StackOverflowError:线程请求的栈深度大于虚拟机允许的深度抛出。

    OutOfMemoryError:如果 JVM 栈容量可以动态扩展,虚拟机栈占用内存超出抛出。

    (4)JVM中的堆:

    堆主要作用是存放对象实例,Java 里几乎所有对象实例都在堆分配内存,堆也是内存管理中最大的一块。Java的垃圾回收主要就是针对堆这一区域进行。可通过 -Xms 和 -Xmx 设置堆的最小和最大容量。

    堆会抛出 OutOfMemoryError异常。

    (5)方法区:

    方法区用于存储被虚拟机加载的类信息、常量、静态变量等数据。

    JDK6之前使用永久代实现方法区,容易内存溢出。JDK7 把放在永久代的字符串常量池、静态变量等移出,JDK8 中抛弃永久代,改用在本地内存中实现的元空间来实现方法区,把 JDK 7 中永久代内容移到元空间。

    方法区会抛出 OutOfMemoryError异常。

    (6)运行时常量池:

    运行时常量池存放常量池表,用于存放编译器生成的各种字面量与符号引用。一般除了保存 Class 文件中描述的符号引用外,还会把符号引用翻译的直接引用也存储在运行时常量池。除此之外,也会存放字符串基本类型。

    JDK8之前,放在方法区,大小受限于方法区。JDK8将运行时常量池存放堆中。

    (7)直接内存:

    直接内存也称为堆外内存,就是把内存对象分配在JVM堆外的内存区域。这部分内存不是虚拟机管理,而是由操作系统来管理。Java通过通过DriectByteBuffer对其进行操作,避免了在 Java 堆和 Native堆来回复制数据。

    (8)java创建对象的过程:

    1、检查该指令的参数能否在常量池中定位到一个类的符号引用,并检查引用代表的类是否已被加载、解析和初始化,如果没有就先执行类加载

    2、通过检查通过后虚拟机将为新生对象分配内存。

  • 相关阅读:
    Golang 数组
    Golang 定时任务库使用
    Golang 选项设计模式
    使用阿里云构建海外docker镜像
    大数相加算法实现
    递归思想和迭代思想
    阶乘函数(factorial)——结果在整型范围内的阶乘计算
    最大公约数和最小公倍数(Greatest Common Divisor and Least Common Multiple)
    日结(2018年12月23日)
    日结(2018年12月22日)
  • 原文地址:https://www.cnblogs.com/KL2016/p/15268964.html
Copyright © 2020-2023  润新知