`
xuyuanshuaaa
  • 浏览: 397614 次
  • 性别: Icon_minigender_1
  • 来自: 大连
社区版块
存档分类
最新评论

java 内存管理

阅读更多
java的垃圾回收功能
jvm的内存管理机制称为垃圾回收机制。合理的管理内存的使用。
垃圾对象的解释:
一个对象创建后被放置在JVM的堆内存(Heap)中,当永远不再引用这个对象时,它将被J1VM在堆内存(heap)中回收。被创建的对象不能再生,同时也没有办法通过程序语句释放它们。

另一种定义是,对象在JVM运行空间中无法通过根集合到达时,这个对象就称为垃圾对象,根集合是由类中的静态引用域和本地引用域组成的。

jvm中有两种形式的内存,堆内存和栈内存,heap和stack。前者主要用来存储程序中在运行时创建的或实例化的对象和变量。后者用来存储程序中,声明为静态的方法。

堆内存用来存放由 new 创建的对象和数组,在堆中分配的内存,由 Java 虚拟机的自动垃圾回收器来管理。在堆中产生了一个数组或者对象之后,还可以在栈中定义一个特殊的变量,让栈中的这个变量的取值等于数组或对象在堆内存中的首地址,栈中的这个变量就成了数组或对象的引用变量,以后就可以在程序中使用栈中的引用变量来访问堆中的数组或者对象,引用变量就相当于是为数组或者对象起的一个名称。引用变量是普通的变量,定义时在栈中分配,引用变量在程序运行到其作用域之外后被释放。而数组和对象本身在堆中分配,即使程序运行到使用 new 产生数组或者对象的语句所在的代码块之外,数组和对象本身占据的内存不会被释放,数组和对象在没有引用变量指向它的时候,才变为垃圾,不能在被使用,但仍然占据内存空间不放,在随后的一个不确定的时间被垃圾回收器收走(释放掉)。栈内存中主要存放静态函数,另外main函数也存储在栈中!!这也是 Java 比较占内存的原因,实际上,栈中的变量指向堆内存中的变量,这就是 Java 中的指针!

java内存分配
     -- 基础数据类型直接在栈空间分配;
     -- 方法的形式参数,直接在栈空间分配,当方法调用完成后从栈空间回收;
     -- 引用数据类型,需要用new来创建,既在栈空间分配一个地址空间,又在堆空间分配对象的类变量;
     -- 方法的引用参数,在栈空间分配一个地址空间,并指向堆空间的对象区,当方法调用完后从栈空间回收;
     -- 局部变量 new 出来时,在栈空间和堆空间中分配空间,当局部变量生命周期结束后,栈空间立刻被回收,堆空间区域等待GC回收;
     -- 数组既在栈空间分配数组名称, 又在堆空间分配数组实际的大小!
Java内存模型
* Java虚拟机将其管辖的内存大致分三个逻辑部分:方法区(Method Area)、Java栈和Java堆。
    -- 方法区是静态分配的,编译器将变量在绑定在某个存储位置上,而且这些绑定不会在运行时改变。
        常数池,源代码中的命名常量、String常量和static 变量保存在方法区。
    -- Java Stack是一个逻辑概念,特点是后进先出。一个栈的空间可能是连续的,也可能是不连续的。
        最典型的Stack应用是方法的调用,Java虚拟机每调用一次方法就创建一个方法帧(frame),退出该方法则对应的  方法帧被弹出(pop)。栈中存储的数据也是运行时确定的
    -- Java堆分配(heap allocation)意味着以随意的顺序,在运行时进行存储空间分配和收回的内存管理模型。
        堆中存储的数据常常是大小、数量和生命期在编译时无法确定的。Java对象的内存总是在heap中分配。

堆内存分配
     JVM初始分配的内存由-Xms指定,默认是物理内存的1/64;
     JVM最大分配的内存由-Xmx指定,默认是物理内存的1/4。
     默认空余堆内存小于40%时,JVM就会增大堆直到-Xmx的最大限制;空余堆内存大于70%时,JVM会减少堆直到-Xms的最小限制。
     因此服务器一般设置-Xms、-Xmx相等以避免在每次GC 后调整堆的大小。
非堆内存分配
     JVM使用-XX:PermSize设置非堆内存初始值,默认是物理内存的1/64;
     由XX:MaxPermSize设置最大非堆内存的大小,默认是物理内存的1/4。
例子
     -Xms256m
     -Xmx1024m
     -XX:PermSize=128M
     -XX:MaxPermSize=256M
堆内存
* 在JVM启动时被创建;堆内存中所存储的对象可以被JVM自动回收,不能通过其他外部手段回收
* 堆内存可分为两个区域:新对象区和老对象区
    -- 新对象区可分为三个小区:Eden区、From区、To区
    Eden区用来保存新创建的对象,当Eden区中的对象满了之后,JVM将会做可达性测试,检测有哪些对象由根集合出发是不可达的,不可达的对象就会被 JVM回收,并将所有的活动对象从Eden区拷到To区,此时一些对象将发生状态交换,有的对象就从To区被转移到From区。
JVM中对象的生命周期  七个阶段
* 创建阶段(步骤)
    -- 为对象分配存储空间
    -- 开始构造对象
    -- 递归调用其超类的构造方法
    -- 进行对象实例初始化与变量初始化
    -- 执行构造方法体
不要再循环中声明变量
如  for(int =0;i<1000;i++)  object obj=new Object();
这样会在内存中存在大量的内存引用。并且给垃圾回收带来很大的负担。
* 应用阶段
    -- 特征:系统至少维护着对象的一个强引用;所有对该对象引用强引用(除非显示声明为其它引用)
强引用
      指JVM内存管理器从根引用集合出发,遍寻堆中所有到达对象的路径。当到达某对象的任意路径都不含有引用对象时,对这个对象的引用就被称为强引用。
当内存不足时,JVM宁愿抛出OutOfMemeryError错误使程序停止,也不会靠收回具有强引用的对象来释放内存空间
-- 软引用
      它能实现cache功能,防止最大限度的使用内存时引起的OutOfMemory异常,在内存不够用的时候jvm会自动回收Soft Reference。
软引用可以和一个引用队列(ReferenceQueue)联合使用,如果软引用所引用的对象被垃圾回收,java虚拟机就会把这个软引用加入到与之关联的引用队列中。
      Java中提供软引用的包:java.lang.ref.SoftReference(后续详解)
import java.lang.ref.SoftReference  
//实现cache功能,最大限度利用内存  
Test test = new Test();  
SoftReference sr = new SoftRefence(test);  
test = null;  
if(sr.get() != null){  
     test = sr.get();  
}else{  
     test = new Test();  
     sr = new SoftReference(test);  
     test = null;  
}  
不可视阶段
    -- 如果一个对象已使用完,并且在其可视区域不再使用,应该主动将其设置为null,即obj=null;这样可以帮助JVM及时地发现这个垃圾对象,并且可以及时地挥手该对象所占用的系统资源。
System.gc();  
Java中的析构方法finalize
    finalize()方法常称之为终止器
          protected void finalize(){
              // finalization code here
         }
    对象即将被销毁时,有时需要做一些善后工作。可以把这些操作写在finalize()方法里。
    Java终止器却是在对象被销毁时调用。一旦垃圾收集器准备好释放无用对象占用的存储空间,它首先调用那些对象的finalize()方法,然后才真正回收对象的内存。而被丢弃的对象何时被销毁,应用是无法获知的。大多数场合,被丢弃对象在应用终止后仍未销毁。到程序结束的时候,并非所有收尾模块都会得到调用。
在C++程序设计中有构造与析构的概念,并且是内存管理技术中相当重要的一部分,而在Java语言中只有构造的概念,却没有析构的概念。这是因为理论上JVM负责对象的析构工作也就是之前讲到的垃圾回收的概念,其实Java语言中的finalize 方法类似于C++语言中的析构函数。finalize 方法是Java语言根基类Object类的一个方法,这个方法是保护类性质的方法(protected),由于在Java应用中开发的所有类都为Object的子类,因此用户类都从Object对象中继承了该方法。因此我们在子类中可以调用父类中的finalize 方法,由于finalize 方法没有自动实现递归调用,我们必须手动实现,因此finalize函数的最后一个语句通常是super.finalize()。通过这种方式,我们可以实现从下到上finalize 的调用,即先释放用户类自身的资源,然后再释放父类的资源。通常我们可以在finalize 方法中释放一些不容易控制、并且非常重要的资源,例如:一些I/O的操作,数据的连接。这些资源的释放对整个应用程序是非常关键的。
    由于GC调用finalize的时间是不确定的,有时我们需要通过其他的手段来释放程序中所占用的系统资源,比如自己在类中声明一个destroy()方法,在这个方法中添加释放系统资源的处理代码,当你使用完该对象后可以通过调用这个destroy()方法来释放该对象内部成员占用的系统资源。并且最好在类的finalize 方法中添加资源释放代码,这样做更为保险、安全。在类深度继承的情况下,这种方法显得就更为有效,我们可以通过递归调用destroy的方法在子类被销毁的时候释放父类所占用的资源
在finalize方法中我们再次调用了destroy方法用来释放其自身所占用的资源,然后调用其超类Object的finalize方法,这是我们以上所提到的“双保险”的内存释放方法
分享到:
评论

相关推荐

    java内存管理详细介绍.doc

    Java内存管理是Java编程中至关重要的一环,它与C++等其他语言的内存管理机制有着显著的区别。在C++中,程序员需要手动管理内存,包括分配和释放,而在Java中,这一过程则由Java虚拟机(JVM)自动进行,通过垃圾收集...

    Java内存管理机制相关资料汇总

    资源名称:Java内存管理机制相关资料汇总资源目录:【】java内存回收机制及预防【】java内存管理机制【】java内存管理白皮书【】Java虚拟机内存管理_对象和引用_空指针【】深入理解java虚拟机jvm高级行与最佳实践...

    java内存管理

    Java内存管理是Java编程中的核心概念,它涉及到程序运行时如何高效地分配、使用和回收内存。在Java中,内存管理主要由JVM(Java Virtual Machine)负责,其中包括了垃圾收集机制,确保程序不会因为内存泄漏而导致...

    java内存管理 ppt

    Java内存管理是Java编程中的核心概念,它涉及到程序运行时数据的存储、分配以及回收。在Java中,内存主要分为堆内存(Heap)和栈内存(Stack),还有方法区(Method Area)、程序计数器(PC Register)以及本地方法...

    java内存管理精彩概述

    Java内存管理是Java核心技术的重要组成部分,对于每个开发者来说,理解其工作原理都是十分必要的。这一主题既实用又有趣。以下是对Java内存管理的精彩概述,主要基于Sun Hotspot JVM,但请注意,不同JVM可能有不同的...

    Java的内存管理机制分析

    通过对Java内存管理机制的深入分析,我们可以了解到Java如何高效地管理和利用内存资源。理解这些机制对于优化Java应用程序的性能至关重要,特别是在处理大规模数据集或多线程环境时。此外,合理配置JVM参数和选择...

    java内存管理白皮书

    《Java内存管理白皮书》深入探讨了Java虚拟机(JVM)中的内存管理机制,特别是Sun Microsystems在J2SE 5.0版本中的HotSpot JVM。本文将根据标题、描述、标签以及部分内容,详细解析Java内存管理的核心知识点,包括...

    JAVA 内存管理总结

    【JAVA 内存管理总结】 Java 的内存管理主要涉及对象的生命周期,包括对象的分配和释放。对象的分配主要是通过 `new` 关键字在堆内存(Heap)中完成,而对象的释放则由垃圾回收机制(Garbage Collector, GC)自动...

    JAVA内存管理模式研究.pdf

    "JAVA内存管理模式研究" 在 Java 编程语言中,内存管理是非常关键的机制之一。 Java 虚拟机(JVM)通过对内存的分配和回收来管理内存资源。 本文将详细介绍 Java 的内存管理模式,包括内存区域、内存分配策略、垃圾...

    java内存管理问题及解决办法

    Java内存管理是Java编程中至关重要的一环,它涉及到程序的性能和稳定性。本文将深入探讨Java内存管理机制,包括垃圾回收、内存分配与释放、内存泄漏及其预防措施,以及四种引用类型的特点和应用场景。 首先,Java...

    java内存管理 .pptx

    Java内存管理是Java编程中至关重要的一环,它涉及到Java虚拟机(JVM)如何高效地运行Java代码。在Java中,内存管理主要包括内存区域的划分、对象的生命周期以及垃圾回收机制。 1. **内存区域划分** - **方法区...

    java内存管理深入讲解

    ### Java内存管理深入讲解 #### 一、Java内存模型概览 Java程序的运行依赖于一个精心设计的内存模型,该模型确保了程序在不同环境中的一致性和高效性。Java内存模型主要包括两个部分:栈(Stack)和堆(Heap)。这...

    关于java内存管理的一些理解

    主要关于java虚拟机的运行时数据区域,参考了周志明的深入理解java虚拟机,还涉及到了native方法、垃圾回收机制等等。

    java内存管理的原理.docx

    Java内存管理的原理是Java开发中的重要组成部分,它关乎到应用程序的性能和稳定性。Java虚拟机(JVM)负责自动管理内存,包括对象的分配和回收,以减轻开发人员的负担。然而,深入理解这些原理可以帮助优化代码,...

Global site tag (gtag.js) - Google Analytics