Java中

时间:2015-08-10 11:50:57

标签: java class object

     public List<Map<String,class1>> methodName(String Parameter)
     {
          //create instance of List
          List<Map<Strig,class1>> list1 = new ArrayList<Map<String,class1>>();

          for(ArrayList arrayList : someGlobalList)
          {
              //create instance of class1
              //Initialize class1 with values in arrayList
              //Put this class1 as a value to tempMap which is created inside this loop
              //Put that tempMap into List
          }
       return list1;
     }  

我怀疑

据我所知,我们无法保证垃圾回收。但是this questionwhen we return a local reference不会被垃圾收集。在我的例子中,class1是一个本地对象。但我正在回归list1。将来自调用者函数的那些对象用作list1.get("key")是否安全。它将返回class1对象。我可以安全地使用班级成员吗?

5 个答案:

答案 0 :(得分:2)

对象仅在您的代码无法再访问对象后才有资格进行垃圾回收。

让我们计算对新创建的对象的引用。每个class1对象目前只从列表中引用,所以让我们看一下列表本身的引用。

您有一个名为list1的引用。

然后返回一个值。这将创建一个第二个引用,该引用放在堆栈中并传递给调用者。

List<...> result = theObj.methodName("foo");

在此过程中,第一个引用(list1)不再可访问,但返回的引用仍可访问 - 在这种情况下,它将被分配给变量result。因此,您仍然有一个有效且可访问的列表引用。因此,列表中的每个引用都是有效且可访问的。

所以是的,使用它是完全安全的。

除Java之外还有其他语言,您可以在 stack 空间中分配对象。也就是说,对象本身是在本地分配的。弹出堆栈帧时,返回对此类对象的引用是不安全的。以C为例,它返回一个指向本地数组开头的指针:

char *bad_string(void)
{
    /* BAD BAD BAD */
    char buffer[] = "local string";
    return buffer;
}

但是在Java中,对象总是在堆空间中分配(除非内部优化对程序员不可见,并且检查是安全的,如评论中所述)。

new运算符分配的对象永远不会弹出&#34;并始终遵守垃圾回收规则。堆栈/本地方法空间仅用于基元和引用,并且您永远不会引用任何对这些对象的引用。因此,如果你有某种东西的引用,你可以相信它的记忆是安全的。

答案 1 :(得分:1)

是的,只要分配了引用,您就能够访问要返回的列表对象(list1)中包含的所有对象(包括class1类型的对象)到调用methodName的方法中的引用变量。 这是因为没有本地对象这样的东西。对象存在于堆中(与堆栈中存在的局部变量不同),如果没有更多可访问的引用,它们将只有资格进行垃圾回收。

答案 2 :(得分:0)

是。片刻1离开帧(由函数返回),它和它的所有引用都不再是&#34;局部变量&#34;并且在不再引用&#34; list1&#34;

之前不会成为垃圾收集的候选者

答案 3 :(得分:0)

  

就我而言,class1是一个本地Object。但我要返回list1

如果某个方法的参考泄漏,那么可以使用该对象(安全?)是另一个依赖于安全的确切定义的问题)。在您返回list1的情况下,list1引用的所有本地字段(递归地)都可以在没有NPE的情况下访问(或担心它们被GCed),因为您的列表具有强引用到那些实例。

如果您正在谈论线程安全性,那么它取决于有多少线程可以访问此泄露的引用。

答案 4 :(得分:-1)

您只需要一个参考。此第一个引用对象引用的对象也将从GC中释放..依此类推树。