Reputation: 4477
If I have a List that I want to trim to save memory, I seem to be able to set the list capacity and then wait for GC to free the memory. When the List gets promoted to the next generation, the memory allocated for it appears to be a function of the list's capacity, rather than the memory originally allocated. This saves me copying explicitly, and ultimately means 1 less copy in total.
var x = new List<double>(50000000) { 1, 2, 3 };
//Lots of memory used here
GC.Collect(2);
//Still lots of memory used
x.Capacity = 3;
GC.Collect(2);
//Much less memory now used
Is it possible to do the same thing somehow with Arrays?
Note that I don't intend to force GC explicitly - this is just to illustrate that when GC does eventually occur, the memory is freed.
Upvotes: 1
Views: 221
Reputation: 61982
Behind the scenes, x.Capacity = 3;
or x.TrimExcess()
will copy all the entries from the private array that holds them, over to a new tiny array. The huge array will then later be collected.
To do something similar for your own array, you can do:
var y = new double[50000000];
//Lots of memory used here
GC.Collect(2);
//Still lots of memory used
Array.Resize(ref y, 3);
GC.Collect(2);
//Much less memory now used
Upvotes: 1
Reputation: 68710
Simply use TrimExcess
of List<T>
.
This is the equivalent of list.Capacity = list.Count
, which allocates a new array of size list.Count
and copies all the elements to it.
You can use the same strategy for arrays, but you'll have to code it yourself though:
int[] arr = new int[50000];
int count = 3;
int[] compact = new int[count];
Array.Copy(arr, compact, count);
arr = null;
Upvotes: 1
Reputation: 9985
I think this is equivalent to your list example
var x = new Double[50000000];
//Lots of memory used here
GC.Collect(2);
//Still lots of memory used
var y = new Double[3];
Array.Copy(x, 0, y, 0, 3);
x = y;
GC.Collect(2);
//Much less memory now used
Upvotes: 0
Reputation: 3695
I'm afraid not. Arrays, by their very nature, are fixed size.
http://msdn.microsoft.com/en-us/library/9b9dty7d.aspx
Specifically:
The number of dimensions and the length of each dimension are established when the array instance is created. These values can't be changed during the lifetime of the instance.
You will be able to free up memory by setting array elements to null, though. And of course, you can resize arrays manually, but that requires you to create another array and copy the relevant elements into it.
Upvotes: 1