因此,我目前正在开发一个程序,该程序需要能够处理数组中存储的大量数据,并且需要一种方法来清除数组中的所有内容。对于以下示例,明智地进行内存存储会不好吗?我知道垃圾收集器最终会为您清理它,但是是否有原因为什么另一个方法(例如for循环并将其中的每个值设置为null)会比这个更好呢?
Object[] objArray = new Object[n];
/*Do some stuff with objArray*/
objArray = new Object[n]
否则,这样做将使此操作在O(1)时间运行,而for循环则需要O(n)。
答案 0 :(得分:5)
这是不好的做法。
首先,为变量分配一个新数组实际上并没有“清除”任何内容(更多内容请参见下文)。
这是最佳做法:
objArray = null;
这会使原始数组无法访问,因此(最终)将被垃圾回收。
这还避免了不必要的内存分配,从而避免创建用于替换旧数组的空数组。
但是,这两个选项都无法“清除”原始阵列,尽管可能会造成很小的安全风险。在清除垃圾之前,如果转储内存内容等,则数组的内容可能是可分割的。
真正清除数组:
Arrays.fill(objArray, null);
答案 1 :(得分:1)
不,这不是一个坏习惯。但是,使数组的所有索引为空将很有可能会更快(从技术上讲,这就是实现细节;但是可以在您的特定系统上对其进行基准测试),因为不需要额外的分配新内存的步骤。但是,建议不要成为所谓的过早优化的受害者,因为如果您以后发现需要进行较大的更改,可能会浪费时间。另外,请记住,由于将继续使用现有的数组对象,因此引用该对象的代码的任何其他部分也将看到对其的更改。
答案 2 :(得分:0)
从技术上讲,这并不重要。
更多关于可读性和意图传达。
您看到,如今您正在努力使对象不可变。如果无法更改,则可以避免各种多线程问题。因此,更新指向新数组的引用与之不完全一致。
值得一提的另一点是:如果您真的想清除数组(至少对于原始类型),则最好迭代该数组并重置其所有插槽。 (显然,这对于引用类型的数组是不可能的)
答案 3 :(得分:0)
这很好,因为您使用的是“原始”数组,而不是任何Collection。您可能对前一个阵列中的内存分配感到不安全,但是不必担心GC会为您清除这些内存。但是,在使用Collections API时,您宁愿调用:
yourCollection.clear()
答案 4 :(得分:0)
Another approach, as used by ByteBuffer, is to keep the original array, leave its contents alone, and overwrite from the beginning. When using the array, use the index of the last element updated to avoid the remainder of the array. "Clearing" the array doesn't really gain anything, unless whatever is processing the array is looking for some specific value to indicate the end of content.
答案 5 :(得分:0)
Typical Java users should not worry about memory management unless security or performance are explicit bottlenecks. See related questions.
If you actually need to have a way to "erase" the array for your logic (i.e mark the array as reset), and since you intend on reusing the array later, you can
use a boolean to mark the array as "unusable" until it has been filled again (better solution if the objects inside the array do not consume too much memory)
fill it with null
rather than assigning null
to it to avoid multiple array allocations (especially if n
is large) in the long run:
Arrays.fill(objArray, null);
.