因为我们写代码的时候很少主动为一个对象设置null.而对象被GC回收的条件是没有被引用。所以我怀疑一个方法的返回会导致一些方法内部对对象的引用被自动清空,无需手动设置null。不知是否这样?

解决方案 »

  1.   

    可以这样说
    方法返回,内部的局部变量没有存活的引用指向它们了,于是就满足回收的条件了
    设置为null,也只是把指向对象数据的引用移开,跟上面的原理是一样的
      

  2.   

    基本上是这样的
    当一个对象不再被其他变量引用的时候,它就满足被回收的条件,当gc发生,那么它就可能被回收。
    手动设置null的目的是为了让变量不再引用对象,一旦方法调用结束,方法栈内的变量就消亡,所以也一样满足没有变量引用对象的回收条件。可以给LZ一段代码
    import java.lang.management.*;
    import java.io.*;public class GCTest {
        public static void main(String[] args) {
            {GCTest gc = new GCTest();} //一个生命周期在{}的对象
            for (int i=0; i<100; i++) { //多个生命周期在for内的对象
                GCTest gc = new GCTest();
                //gc = null; //其实这个null设置有无关系不大,即使设置null,也不能保证立刻被回收
            }
            GCTest gc = new GCTest(); //一个生命周期在main方法内的对象
            System.gc(); //这里模拟发生了垃圾回收,如果没有这里
                            //可以考虑把sleep时间延长,让系统自己发生回收
                            //或者去掉sleep,也不调用gc方法,看看即使设置了null是不是保证立刻被回收
            try {Thread.sleep(5000);} catch (Throwable e) {e.printStackTrace();}
            printMemo("test.txt"); //把内存信息打印到文件,在打印结果中查找GCTest,看看程序执行到这里时有几个GCTest实例
        }    public static void printMemo(final String file) {
            try {
                System.out.println(ManagementFactory.getRuntimeMXBean().getName());
                String pid = ManagementFactory.getRuntimeMXBean().getName().replaceAll("(\\d+)@.*", "$1");
                //String cmd = "jmap -dump:file=" + file + " " + pid;
                String cmd = "jmap -histo " + pid;
                System.out.println(cmd);
                final Process p = Runtime.getRuntime().exec(cmd);
                Thread t = new Thread() {
                    public void run() {
                        BufferedReader br = new BufferedReader(new InputStreamReader(p.getInputStream()));
                        String buf;
                        try {
                            PrintStream ps = new PrintStream(new FileOutputStream(file));
                            while ((buf=br.readLine()) != null) {
                                ps.println(buf);
                            }
                            ps.close();
                        } catch (Exception e) {
                            e.printStackTrace();
                        }
                    }
                };
                t.start();
            } catch (Throwable e) {
                e.printStackTrace();
            }
        }
    }
      

  3.   

    没有必要手动设为null,除非是静态对象