【问题标题】:Java memory usage - is this syntax correct or it will cause a memory leak?Java 内存使用 - 这种语法是否正确或会导致内存泄漏?
【发布时间】:2016-08-17 15:10:02
【问题描述】:
HashMap obj = new HashMap();
for(int i=0;i<1000;i++) {
    obj = getObjects(i);
}

这段代码会在“obj = getObjects(i);”这一行导致内存泄漏吗?

我不确定 obj 的旧值是否被释放,或者它们是否仍在使用内存。

如果这是内存泄漏,正确的语法是什么?

【问题讨论】:

  • obj 在分配之前指向的 HashMap 将被垃圾收集,因为不会有任何对它的引用,但不能保证它会在分配完成后立即发生。垃圾收集最终会发生。
  • 请不要使用像 HashMap 这样的原始类型。

标签: java memory memory-leaks garbage-collection


【解决方案1】:

我做了一个测试,很好,java是定期释放内存。 我仍然使用 HashMap 来重现我的应用程序上下文。

package memtest;

import java.util.HashMap;

public class MemTest {
    public static void main(String[] args) throws InterruptedException {
        HashMap obj = new HashMap();
        int loop = 1;
        while(true) {
            HashMap newObj = new HashMap();
            newObj.put("1", "big string that is not pasted here");
            obj = newObj;
            System.err.println("At loop "+loop);
            Thread.sleep(1000);
            loop++;
        }
    }    
}

【讨论】:

    【解决方案2】:

    这段代码会在“obj = getObjects(i);”这一行导致内存泄漏吗?

    无法确定。您还没有向我们展示getObjects 的代码,并且该方法有可能(尽管根据方法的名称不太可能)存在内部内存泄漏。

    但是,重复分配对简单变量(例如obj)的引用不会泄漏内存。

    我不确定 obj 的旧值是否被释放,或者它们是否仍在使用内存。

    事情没那么简单:

    • 从存储管理的角度来看,“obj 的旧值”是引用……而不是对象。
    • 当您为 obj 分配不同的引用时,这些引用所引用的对象不会立即释放。
    • 它们最终将在未来由 GC 发布,前提是:
      • 有足够的内存压力导致 GC 为已分配对象的“空间”运行,并且
      • 没有其他引用对象。

    如果这是内存泄漏,正确的语法是什么?

    郑重声明,内存泄漏不是语法问题。

    【讨论】:

      【解决方案3】:

      引用或对象在被覆盖时不会“释放”。将引用分配为将一个 int 分配给变量没有更多工作。

      相反,旧的引用不再存在,GC 会寻找仍然存在的引用。

      【讨论】:

        【解决方案4】:

        在 java 中有一个垃圾收集器,所以使用像这样的正常操作很难导致内存泄漏。垃圾收集器四处释放所有不再引用的内存。

        有关垃圾收集的更多信息:http://www.oracle.com/webfolder/technetwork/tutorials/obe/java/gc01/index.html

        简短的回答是您的代码不应导致内存泄漏。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多