我的代码中有一个循环,它生成许多 byte[] 数组(每个数组大约 1 到 2 MB),用数据填充它们,然后丢弃引用。因此,即使引用只保留了很短的时间,我也可以看到私有工作集在增长。
现在,如果我尝试在循环后分配一个大数组(~ 400 MB),我会得到内存不足的异常吗?还是分配会强制 GC 收集瞬态数据?
谢谢!
我的代码中有一个循环,它生成许多 byte[] 数组(每个数组大约 1 到 2 MB),用数据填充它们,然后丢弃引用。因此,即使引用只保留了很短的时间,我也可以看到私有工作集在增长。
现在,如果我尝试在循环后分配一个大数组(~ 400 MB),我会得到内存不足的异常吗?还是分配会强制 GC 收集瞬态数据?
谢谢!
生成许多 1-2MB 数组是个坏主意。即使您避免出现内存不足的情况,性能也会受到影响。在大对象堆上分配许多短期对象是当前 GC 不能很好处理的分配模式。
我强烈建议尽可能回收它们。实现一个池,一旦您不再需要它们,就将它们扔到其中。然后在分配时首先检查您是否可以满足来自池的请求。这种模式在我的一个程序中带来了巨大的性能优势。
我认为全内存会强制进行 GC,但如果非托管分配发生在同一时间,您仍然可以获得 OOM。
如果你担心它,你可以随时调用 GC.Collect(); 在循环之后的那个大数组之前,这将强制所有代的垃圾收集。但是不要在循环中做,除非你不关心时间,因为这可能会很慢(对于循环来说太慢了,对于一次性的事情来说不是那么慢。)
这真的取决于。你不能确定垃圾收集器会及时丢弃。使用字节数组你是相当安全的,但是如果你大量使用它们而不使用该dispose()
方法,大多数对象都被丢弃得太晚了。
即使您可能已丢弃所有引用,这也会导致内存不足异常。
如果您遇到问题,可以尝试GC.Collect(0);
,尽管这通常是不可取的。