• JAVA 中的类


    一:类的生命周期

      类的生命周期从类被加载,连接和初始化开始!
         到类的卸载结束!
         01.类的生命周期中,类的2进制数据位于方法区;
         02.在堆中会有一个描述这个类的Class对象;

    2.1 加载:    需要类加载器
       将class字节码文件内容加载到内存中,并将这些静态数据转化成
       方法区中运行时数据结构!在堆中生成一个Class对象;
       这个Class对象就是方法区类数据的访问入口!

    2.2 链接:
       01.类的验证    在编译期间
            合法???
           001.类文件的结构检查
           002.语义检查   比如说final修饰的变量在编译期间发现再次赋值
           003.字节码验证,确保字节码能被jvm识别

    02.类的准备
          为类中所有static修饰的内容开辟空间,并且赋予初始值!!!
          static  int  num =100;
          这时候 num=0;

    03.类的解析
          把类中所有的符号引用转换成直接引用!

           符号引用:就是用字符串的形式来表示某个变量或者是类,我们能看懂
              String  a="a";  Student  stu=new Student();
              a,stu都是符号引用!
           直接引用:是根据符号引用翻译出来的地址!

    2.3 初始化

      加载不是初始化!
      初始化指的是实例化!创建出类的实例!

    初始化的时机:
        01.类的主动引用
           001.new一个类的对象
           002.通过反射的newInstance()
           003.再初始化子类的时候必须先初始化父类
       
    02.类的被动引用
           001.通过类名访问静态的内容
           002.调用类的静态常量也不会初始化类
           003.用类作为对象数组存在时,也不会初始化类
           004.子类调用父类的静态变量不会加载子类的静态代码块(不会执行类的准备阶段)

    三:垃圾回收机制(GC)

    3.1:为什么需要垃圾回收机制
        01.只要是对象被创建,那么就会在虚拟机的堆中开辟空间;
        02.程序运行过程中会创建N个对象,每个对象都会有自己的空间;
        03.如果每个对象都永久的占有这块内存空间,显然内存是不够的!

        为了保证其他的对象能够被正确的创建!

    在C语言中,垃圾回收的任务是程序猿自身负责!
    可能出现的问题:
       01.由于程序猿的粗心大意,导致没有及时释放不使用的对象,释放错误!
       02.程序猿一旦释放了程序核心对象(比如说系统对象),系统崩溃!

    3.2:垃圾回收机制的定义

          在java程序运行过程中,JVM中有一个专门负责回收那些不再使用的对象所占用的内存!
          这种回收的过程,我们称之为垃圾回收机制(GC,Garbage  Collection)!

    3.3:垃圾回收机制的特点

         01.减轻了程序猿进行内存管理的负担;
         02.防止系统内存被非法释放,使我们的程序更加健壮;
         03.只有在对象不被任何变量引用时,才能被回收;
         04.程序无法强制让垃圾回收器立即回收垃圾操作;
         05.当垃圾回收器将要回收不用对象的内存时,会先调用这个对象的finalize()
            这个方法有可能使对象复活,导致垃圾回收器取消对该对象内存的回收。


    3.4:对象的状态

       在java虚拟机的垃圾回收器来看,堆中所有的对象都有3种状态!

       01.可触及状态
       02.可复活状态
       03.不可触及状态

       只有对象处于不可触及状态的时候,垃圾回收期才会真正的释放对象所占有的内存!


        1.对象的生命周期开始 (new语句或者是反射中newInstance)    可触及状态
        2.对象不在被引用,或者对象调用了finalize()               可复活状态
        3.对象调用了finalize()                                 不可触及状态
        4.垃圾回收
        5.对象的生命周期结束

    3.5:垃圾何时被回收(触发GC的条件)
       
        01.对象没有引用===》对象处于不可触及状态
        02.程序在作用域正常执行完毕之后
        03.System.exit()
        04.程序以外终止

     
    3.6:详解GC
        01.什么时间===》触发GC的条件
            001.System.gc()可能触发;
            002.系统自身决定GC的触发时机
                根据Eden区和From Space区的内存大小来决定!
              
        02.对什么东西
             java中的对象===》通过分析算法无法找到的对象

        03.做了什么   
              对搜索到的对象进行复制操作;
              对搜索不到的对象执行finalize()。


       如果真正的回收一个对象,要至少需要两次标记!
       01.第一次标记:对于一个没有其他对象引用的时候;执行finalize()
       02.第二次标记:针对于筛选过的对象,进行回收。


    3.7:java中内存分配机制

         核心:分代分配,分代回收!

    新生代(Young Generation)
       Eden     区   :是连续的内存空间,所以分配内存极快
       Survivor 区    :From  To 必须有一个区域是空的=
    老年代(Old Generation)
    永久代(Permanet Generation)===》方法区
       回收两种数据:
           01.常量池中的常量
           02.无用的类信息
       什么时候回收?
           01.类所有的实例都被回收了
           02.加载类的ClassLoader也被回收了
           03.类对应的Class对象没有被引用   

     


     注意点:
       01.绝大多数创建的对象被分配在Eden区,但是大多数对象会在这个区域死亡!
       02.当Eden区满的时候,会执行Minor GC(Young GC),将死亡的对象清理掉,
          剩余存活的对象存放到survivor0区(survivor1区必然为空)
       03.以后每次Eden区满的时候,会执行Minor GC,所有存活的对象又被放进survivor0区
       04.当survivor0区满的时候,会把存活的对象复制到survivor1区,之后清空survivor0区!
       05.反复执行之后,仍然活着的对象复制到老年代!
       06.老年代的内存比年轻代要大,但是也有满的时候,当老年代满的时候执行Major GC(Full GC)
       07.如果对象比较大,年轻代存放不下,就会直接把对象放进老年代!

     


    Young GC和Full GC的区别:
    01.Young GC是在新生代的Eden区满,Survivor区满的时候触发
       Full GC 是在老年代满的时候触发
    02.Young GC执行的频率高
       Full GC 执行的频率低

    什么时候触发Full GC
     01.执行System.gc(),系统建议执行Full GC,但不是必须执行
     02.老年代空间不足
        001.当Young GC执行后存活的对象需要进驻老年代,但是发现老年代空间不足
        002.当Survivor0区,Survivor1区来回切换时,发现内存不足,必须放进老年代,而且老年代空间不足
     03.方法区空间不足

     

    3.8:GC涉及到的算法


      01.引用计数法  Reference Counting
          给对象增加一个引用计数器,使用一次引用+1,少一个引用-1!
          当引用为0的时候回收!
          但是不能解决循环引用的问题!

      02.根搜索算法 GC Roots Tracing
          对象以根作为起点,向下延伸,延伸的路径我们称之为 引用链(Reference Chain)
          当一个对象没有任何引用链连接时,证明这个对象时不可用的对象(不可达),会被回收!

          什么是根?
          01.方法区中常量引用的对象
          02.栈中引用的对象
          03.静态属性引用的对象

      03.复制算法  Copying   
         就是将原有的内存空间分为两块,每次只能使用其中一块!
         缺点就是浪费一半的内存空间!比标记-清除算法要高效!
         不适合存活对象较多的区域使用!
         在新生代使用!

      04.标记-清除算法  Mark-Sweep

         001.把所有存活的对象打个标记
         002.把所有没有标记的对象统一清除
       
        缺点:
            01.两个过程效率都慢,因为需要想查询
            02.因为在清除过程中会产生内存碎片,如果有大对象将无法存储
     
      04.标记-整理算法  Mark-Compact
          适合存活对象多的区域,所以适合在老年代使用!
         
      
     

  • 相关阅读:
    经典算法以及案例总结
    supervisor的介绍
    快速排序算法
    mysql 省市联动sql 语句
    前段验证框架 formValidator
    css 之!important
    js 倒计时
    js 设置url 参数值
    java 获取指定日期
    js 日期控件laydate使用
  • 原文地址:https://www.cnblogs.com/wh1520577322/p/9379954.html
Copyright © 2020-2023  润新知