Understanding F # Memory Consumption
I've been playing with F # lately and wrote this little snippet below, it just creates a series of randomized 3d vectors, puts them into a list, matches each vector in length and sums all those values.
Running the program (as a Build.exe release, not an interactive one), the binary consumes in this particular case (10 million vectors) about 550MB of RAM. A single Vec3 object should account for 12 bytes (or 16, assuming some alignment is performed). Even if you do some rough math with 32 bytes to account for some storage overhead (bytes per object * 10M / 1024/1024), you're still 200MB of actual consumption. I naively believe that in the end I will have 10 mio * 4 bytes per single, since the Vec3 objects are "imprinted".
So far, my guess is: Either I leave one (or more) copy / copies of my list somewhere and I don't know about it, or are some intermediate results never going to be garbage collected? I can't imagine that inheriting from System.Object comes with a lot of overhead. Can anyone point me in the right direction?
Tia
type Vec3(x: single, y: single, z:single) =
let mag = sqrt(x*x + y*y + z*z)
member self.Magnitude = mag
override self.ToString() = sprintf "[%f %f %f]" x y z
let how_much = 10000000
let mutable rng = System.Random()
let sw = new System.Diagnostics.Stopwatch()
sw.Start()
let random_vec_iter len =
let mutable result = []
for x = 1 to len do
let mutable accum = []
for i = 1 to 3 do
accum <- single(rng.NextDouble())::accum
result <- Vec3(accum.[0], accum.[1], accum.[2])::result
result
sum_len_func = List.reduce (fun x y -> x+y)
let map_to_mag_func = List.map (fun (x:Vec3) -> x.Magnitude)
[<EntryPoint>]
let main argv =
printfn "Hello, World"
let res = sum_len_func (map_to_mag_func (random_vec_iter(how_much)))
printfn "doing stuff with %i items took %i, result is %f" how_much (sw.ElapsedMilliseconds) res
System.Console.ReadKey() |> ignore
0 // return an integer exit code
source to share