微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

如何在Java中删除有效最终数组

如何解决如何在Java中删除有效最终数组

我想通过在使用完引用后null删除对大型数组的引用来删除它。但是,这给了我一个编译器错误,因为对数组的并行分配要求数组(有效地)为最终数组(至少我认为这是问题所在……)。如何允许垃圾回收删除数组?

double[][] arr = new double[n][n];
IntStream.range(0,n).parallel().forEach(i -> {
    for(int j=0;j<i;j++) {
        directdistances[i][j] = directdistances[j][i] = ...;
    }
});

//Use arr here...

arr = null; //arr no longer needed.
//This gives the error "Local variable defined in an enclosing scope must be final or effectively final."

解决方法

我想删除使用大数组后对它的引用,将其删除,将其删除。

不要。

我在JVM领域中了解的所有实现都将扫描线程堆栈以找出可访问的对象。这意味着该方法的 scope 无关与对象保持活动状态的时间无关。用简单的话来说:

void yourMethod(){
    
      byte [] bytes = ....
      // use bytes array somehow
 
      // stop using the byte array
      // .... 10_000 lines of code

      // done
}

// stop using the byte array行之后,bytes IS 可立即进行垃圾回收。方法结束后 将不再合格。方法的范围(介于{}之间的所有内容)不会影响bytes保持存活的程度。 here is an example that proves this

,

最晚在方法返回时,该数组将成为可进行垃圾收集的条件-您无需将其设置为null。

如果您的方法比较长,并且担心数组的其余部分会保留在数组中,则解决方案是编写较小的方法。将功能划分为较小的方法还可以提高可读性和可重用性。

如果您不能或不想编写较小的方法,则在方法中引入单独的块可能会有所帮助。局部变量声明是该块的局部变量,因此,该“技巧”还使您可以在该方法的不同块中重用变量名。

void largeMethod() {
    first: {
        final int number = 1;
    }
    second: {
        final int number = 2;
    }
}

从技术上讲,该数组在最后一次使用which can be in the middle of the method之后-在该变量超出范围之前,才有资格进行垃圾回收。 section 12.6.1 in the language specification已明确允许:

可以设计程序的优化转换,以减少可到达的对象数量,使其少于天真的被认为可到达的对象数量。例如,Java编译器或代码生成器可能会选择设置不再用于 null 的变量或参数,以使此类对象的存储可能更快地被回收。

虽然规范允许进行此优化,但它不需要。如果您发现优化不是在特定情况下进行的,则需要更好的保证,那么将大方法拆分为小方法将有所帮助。

,

使用AtomicReference ar = new AtomicReference () ; ar. set(arr) ; 这将为您提供有效的最终阵列 然后使用ar.set()和ar.get()方法修改数组

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。