计算机cae全称是什么,gc计算机术语
GC(垃圾收集)是各大语言的宠儿,也是计算机科学领域的热门话题。我第一次在JVM上看到这个算法,后来发现连js这种脚本语言都有GC。就JVM而言,GC算法也在不断完善和成熟。从最早的串行到高顿吞吐量的并行,CMS(Concurrent Mark Sweep)进化为解决高延迟,G1发展为解决碎片化问题。
为什么我们需要GC?
在早期的编程语言中,程序运行过程中没有栈帧需要维护,所以采用静态分配策略,比动态分配快很多,但是有一个很不人性化的缺点,就是需要在编译时确定程序需要的数据结构大小。
1958年,Algol-58语言首次提出了块结构,通过在内存中应用堆栈帧来实现按需分配的动态策略。当过程被调用时,框架将被推到堆栈的顶部,并在调用结束时弹出。堆栈分配策略给了程序员很大的自由度,局部变量在不同的调用过程中有不同的值,为递归提供了基础。然而,后进先出(LIFO)堆栈限制堆栈帧的生命周期不能超过其调用方,并且因为每个堆栈帧都有固定的大小,所以过程的返回值也必须在编译时确定。于是一种新的内存管理策略————堆管理诞生了。
现在计算机VS图灵机
与图灵机相比,现代计算机的本质区别在于它的资源是有限的,所以各种资源用完之后就要释放。
用GC释放所有资源可以吗?
GC本来是给Maha的程序员用的,人很容易手动释放资源,那么每次需要释放资源的时候可以调用GC算法吗?我以为已经一劳永逸了。
不会,GC也有其适用和不适用的场景。在(socket/file handle)的使用中没有用到GC,很大程度上是因为它的不确定性。就算打电话给GC,也不知道什么时候回收,回收不回收。这样的GC还是不靠谱的(雾,GC都是搞笑饼干。
但是,如果我们表明资源是循环利用的,那就不一样了。调用close/destroy后,资源将被100%释放。
为什么可以在内存中使用GC?原因有二。第一,它具有排他性(当然,你也可以称之为唯一性)。OS分配给每个正在运行的程序的内存是唯一的,并且彼此独立。他们为什么互不干涉?以后我回收也不会影响你。第二点是内存够用,日常使用程序我没见过内存占用太多的。以后回收也不会OutOfMenmory,可以放心使用GC的回收机制。
从这两点可以看出,对于一些资源紧张的嵌入式设备,还是手动释放资源比较好。(不包括草莓派)
什么是GC?
GC的本质是自动管理内存,用来回收堆中不再需要(使用)的对象。
我们知道,内存实际上可以分为各种区域,常见的有堆栈和堆。堆栈包含局部变量,这些变量将在函数被调用后被收集。这是一个固定的过程,所以不需要GC。堆中的空间用于在多个函数之间共享数据,程序本身是动态应用的。这时候就需要利用GC了。
GC由两个内核组成。
物体识别,其实就是常说的判断一个物体是不是活的,活的物体,垃圾。
回收算法,何时以及如何回收
那我该怎么办?
先从物体识别开始,确定物体是活体还是包包。
在堆中,基本上都是Java对象的实例。当一个对象没有被引用并且不会被再次引用时,它可以被认为是一个垃圾。
计数(Python和PHP都使用这种方法)
给一个对象一个引用计数器(在对象头上加一个计数器)。参考成功时,计数器加1,参考失败时,计数器减1。当引用数为0时,对象将失败。
这和OS中的PV原语很像。它的实现非常简单高效。但是缺点也很明显,就是很难解决对象之间的回收问题。
举个栗子。如果现在有两个对象OA OB,OA.instance=OBOB.instance=OA两者互相引用,导致计数器不为0,所以两者都不回收。
可访问性分析(跟踪)
这是现代语言最广泛使用的方式。从根对象开始,我们一直追踪,找到所有可以引用的对象。那么这些对象就可以称为可达对象,剩下的对象自然是不可达对象,作为垃圾回收。
那么,你说的这个根对象,它长什么样?
Java堆栈中引用的对象(堆栈框架中的局部变量表)
局部方法堆栈中引用的对象
方法中常数引用的对象
方法中类的静态属性引用的对象。
堆中对象引用的对象,它们不是根,这样就不会造成循环引用的问题。
引用
确定一个物体是否有生命,与“参照物”有关。在JDK 1.2之前,Java中引用的定义非常传统。一个对象只能被引用或不被引用。我们希望描述这类对象:当有足够的内存空间时,它会留在内存中;如果垃圾收集后内存空间仍然非常紧张,可以丢弃这些对象。很多系统的缓存功能都符合这样的应用场景。
在JDK 1.2之后,Java扩展了引用的概念,将其分为以下四种类型。不同的引用类型主要反映了对象不同的可达状态,以及垃圾收集的影响。
强引用
类似“Object obj=new Object()”的引用是强引用。只要存在强引用,垃圾收集器就永远不会回收被引用的对象。但是,如果我们错误地保留了一个强引用,比如给一个静态变量赋值,那么这个对象就会长时间不被回收,导致内存泄漏。
软引用
软引用是一种相对强弱的引用,可以让对象免于一些垃圾回收。只有当JVM认为内存不足时,才会尝试回收软引用指向的对象。JVM将确保在抛出OutOfMemoryError之前清除软引用所指向的对象。软引用通常用于实现对内存敏感的缓存。如果还有空闲内存,可以暂时保留缓存,内存不足时再清理。这确保了缓存在使用时不会耗尽内存。
弱引用
弱引用比软引用更弱。JVM在做垃圾回收的时候,不管有没有足够的内存,都会回收只和弱引用关联的对象。
幻象参考
虚拟引用,也称为幻影引用,是最弱的一种引用关系。对象是否有虚拟引用对其生存期没有影响。它只提供了一种机制来保证对象在被终结后会做一些事情,比如通常用来做所谓的事后清理机制。
其实软指称、弱指称、虚指称都可以称为弱指称。
通过弱引用指向一个对象,这不会保护该对象免于GC回收。如果对象被回收,弱引用将被赋予一个安全值(通常为NULL)。
涉及