字符串有问题
基本上在Java中,引用(在幕后使用的东西)将主导大多数业务应用程序的内存。它们的创建方式决定了它们在 JVM 中消耗多少内存。String
char[]
仅仅因为它们是大多数业务应用程序作为数据类型的基础,并且它们也是最需要内存的应用程序之一。这不仅仅是Java的事情,数据类型在几乎所有语言和运行时库中都占用了大量的内存,因为至少它们只是每个字符1字节的数组,或者更糟的是(Unicode),它们是每个字符多个字节的数组。String
有一次,在分析一个也具有Oracle JDBC依赖项的Web应用程序上的CPU使用情况时,我发现它比所有其他方法调用的总和主导CPU周期多了好几个数量级,更不用说任何其他单个方法调用了。JDBC驱动程序做了很多很多的操作,有点像使用一切的权衡。StringBuffer.append()
String
PreparedStatements
你所关心的你无法控制,无论如何都不能直接控制
你应该关注的是你控制中的内容,即确保你不会坚持引用的时间超过你需要的时间,并且你不会不必要地重复事情。Java中的垃圾回收例程经过高度优化,如果您了解其算法的工作原理,则可以确保您的程序以最佳方式运行,以使这些算法正常工作。
Java 堆内存不像其他语言中的手动管理内存,这些规则不适用
在其他语言中被认为是内存泄漏的内容与Java及其垃圾回收系统中的内存泄漏不是一回事/根本原因。
在Java内存中,最有可能的是,它不会被一个泄漏的uber对象消耗(在其他环境中悬挂引用)。
很可能是许多较小的分配,因为/ 对象在第一个实例化时大小不合适,然后必须自动增加数组以容纳后续调用。StringBuffer
StringBuilder
char[]
append()
这些中间对象的保留时间可能比垃圾回收器预期的要长,因为它们所在的范围以及运行时可能变化的许多其他内容。
示例:垃圾回收器可能会决定有候选项,但是因为它认为还有足够的内存需要使用,因此在那个时间点将它们清除出去可能太昂贵了,并且它会等到内存压力变高。
垃圾收集器现在真的很好,但它不是魔法,如果你正在做退化的事情,它会导致它不能以最佳状态工作。互联网上有很多关于所有版本的JVM的垃圾回收器设置的文档。
这些未引用的对象可能只是没有达到垃圾回收器认为需要它们才能从内存中删除的时间,或者可能有其他对象()持有对它们的引用(例如,您没有意识到仍然指向该对象。这就是Java中最常见的泄漏,更具体地说,这是一个引用泄漏。List
例:如果您知道您需要使用不使用默认值创建4K,则创建它,就像32一样,并且将立即开始创建垃圾,这些垃圾可以表示您认为对象应该大小的许多倍。String
StringBuilder
new StringBuilder(4096);
您可以发现使用 VisualVM 实例化了多少种类型的对象,这将告诉您需要了解的内容。不会有一个大的闪光灯指向单个类的单个实例,上面写着“这是大内存消耗者!”,也就是说,除非你正在读取一些大文件的某个实例,这也是不可能的,因为许多其他类在内部使用;然后你几乎已经知道了。char[]
char[]
我没有看到任何提及OutOfMemoryError
你的代码中可能没有问题,垃圾回收系统可能没有足够的压力来启动和释放你认为应该清理的对象。您认为有问题的可能不是,除非您的程序崩溃了。这不是C,C++,Objective-C或任何其他手动内存管理语言/运行时。你不能在你期望的细节级别决定记忆中的内容。OutOfMemoryError