当前位置: 首页 > 知识库问答 >
问题:

有关垃圾收集器和finalize()方法的问题

颜鸿云
2023-03-14

我在读关于Java的垃圾收集和finalize()方法的书,有一些疑问引起了我的注意。抱歉,如果你认为这些怀疑真的很愚蠢。

>

垃圾收集器如何知道它需要执行?例如,我有一个部署在服务器上的应用程序,那么垃圾收集器什么时候执行?它是否定期执行,或者当一些(比如1MB)垃圾被收集并执行触发器时,或者它只是随机的,没有办法确定它什么时候执行?

由于垃圾回收机制没有发生,它如何降低应用程序的性能?

假设我的堆中有很多垃圾,但是垃圾收集器没有被执行。如果发生这种情况,那么这不是一个坏行为还是JVM的缺陷?

考虑到我们作为程序员足够聪明,并且知道什么时候需要处理“不那么引用”的指针,我们能说在C/C中手动完成的垃圾收集比在Java中更好吗?

共有3个答案

巫马翰翮
2023-03-14

[1]finize调用是垃圾回收机制的一部分。

[2]垃圾回收器的策略和调用是实现的细节。因此这里没有答案。

[3,4]如果你有很多小垃圾,收集器可能不会执行垃圾收集。这个HOWER可能浪费内存(我认为它是内存泄漏),如果“微小”对象保存内存,收集器就不知道(图像可以用一个微小的句柄/指针来表示本机内存)。

[5]C的概念非常不同(此处省略C)。析构函数可以在一个确定点执行以释放分配的资源(见: RAII)。

申屠新觉
2023-03-14

>

  • finalize()方法总是在垃圾收集对象之前被调用。没有“垃圾收集器方法”。

    垃圾回收器会随时运行。作为程序员,你不能控制它。从技术上讲,你可以通过制造大量垃圾或调用System.gc()来控制它,但你不需要这样做。

    html" target="_blank">垃圾回收器将在需要的时候运行。作为程序员,您不需要担心垃圾回收机制的性能,但是有一些命令行选项可以调整垃圾回收器的行为。

    如果内存不足而垃圾收集器没有运行,那就是JVM缺陷。不过,它会运行。垃圾收集器将在需要时和高效时运行。如果在收集垃圾之前让垃圾堆填满更有效,那么它就会这样做。

    这是一个非常主观的问题,双方都有很好的理由。Java的垃圾回收机制减少了编程错误,但C和C的手动内存管理提供了更一致的性能和内存使用。

  • 魏成济
    2023-03-14

    >

    您可以调整不同的算法来决定何时进行垃圾收集。此外,它还取决于分配给JVM的堆大小(以及其他参数,如新旧代大小、幸存者空间大小等)。如果你使用的是小型应用程序,通常默认配置就足够了。如果你正在编写大型应用程序,需要考虑性能随着时间的推移、CPU时间和暂停时间(有时GC暂停整个应用程序),那么你最好阅读堆内存模型和不同的GC算法和参数来调整GC以更好地满足你的需求。

    应用程序性能受发生的GC周期(而不是不发生的GC周期)的影响。例如,如果堆太小,就会有频繁的循环。如果堆太大,那么循环的频率会降低,但每个循环的执行时间可能会更长。同样,这一切都取决于您选择的GC算法和调优参数,以及堆内存分配(年轻一代有多少内存,老一代有多少内存,幸存空间比等等)

    我看不到这样的场景:你有很多垃圾,没有收集,除非还有足够的空间来分配新的对象。当空间用完或即将用完时(取决于您选择的收集算法、堆大小和其他参数),将有一个收集。

    Java垃圾收集器解决了程序员在非托管语言(如CC)中遇到的一个痛苦的问题。它有它的优点和缺点。当你需要对内存进行绝对控制时,你会使用C。当你想更容易地编写系统,并且不介意为GC分配一些额外的内存,并且与GC共享一点CPU时间时,你可以用java编写得更快(也更健壮——因为内存泄漏和其他讨厌的东西更少)。

     类似资料:
    • 本文向大家介绍Lua 垃圾收集器-__gc元方法,包括了Lua 垃圾收集器-__gc元方法的使用技巧和注意事项,需要的朋友参考一下 示例 5.2 lua中的对象被垃圾收集。有时,您需要释放一些资源,打印消息或在销毁(收集)对象时执行其他操作。为此,您可以使用元__gc方法,当对象被销毁时,该元方法将以对象作为参数进行调用。您可能会将此元方法视为一种析构函数。 此示例显示了__gc运行中的元方法。当

    • Java 15 使 ZGC、Z 垃圾收集器成为标准功能。它是 Java 15 之前的一个实验性功能。它是低延迟、高度可扩展的垃圾收集器。 ZGC 是在 Java 11 中作为一项实验性功能引入的,因为开发人员社区认为它太大而无法提前发布。 即使在机器学习应用程序等海量数据应用程序的情况下,ZGC 也具有高性能和高效工作。它确保在处理数据时不会因垃圾收集而长时间停顿。它支持 Linux、Window

    • Java 15 使 ZGC、Z 垃圾收集器成为标准功能。它是 Java 15 之前的一个实验性功能。它是低延迟、高度可扩展的垃圾收集器。 ZGC 是在 Java 11 中作为一项实验性功能引入的,因为开发人员社区认为它太大而无法提前发布。从那时起,对这个垃圾收集做了很多改进,例如 - 并发类卸载 取消提交未使用的内存 支持班级数据共享 NUMA 多线程堆Pre-touch 最大堆大小限制从 4 T

    • 问题内容: 我从带有node.js的线程垃圾收集中学到了node.js使用世代GC。 我通常使用循环对象引用(最终我都会删除/确保超出范围),并想知道node.js是否能很好地处理它们。所以例如。如果使用参考完成。计数,会有一个问题,所以我想知道这个节点有多好。 一些使用场景: 对于每个http请求,我创建一个带有lambda的setTimeout,该lambda可能引用了范围对象。作用域对象还引

    • 一、垃圾收集算法 1.标记-清除算法 最基础的收集算法是“标记-清除”(Mark-Sweep)算法,如同它的名字一样,算法分为“标记”和“清除”两个阶段。 ①首先标记出所有需要回收的对象 ②在标记完成后统一回收所有被标记的对象。 不足: 效率问题:标记和清除两个过程的效率都不高 空间问题:标记清除之后产生大量不连续的内存碎片,空间碎片太多可能会导致以后程序运行过程中需要分配较大对象时,无法找到足够

    • 问题内容: 是否有可能使Go中的垃圾收集器处理并释放通过C代码分配的内存?抱歉,我之前没有使用过C和cgo,因此我的示例可能需要澄清。 假设您有一些要使用的C库,并且该库分配了一些需要手动释放的内存。我想做的是这样的: 当Go运行时中没有对* Stuff的引用时,垃圾收集器是否可以调用Stuff.Free()? 我在这里有意义吗? 也许更直接的问题是:是否有可能通过编写一个在该对象的引用为零时运行