Aquí es lo que veo (después de insertar un print
antes de la última performGC
, para ayudar a la etiqueta cuando las cosas suceden
524288 524296 32381000 0.00 0.00 1.15 1.95 0 0 (Gen: 0)
524288 524296 31856824 0.00 0.00 1.16 1.96 0 0 (Gen: 0)
368248 808 1032992 0.00 0.02 1.16 1.99 0 0 (Gen: 1)
0 808 1032992 0.00 0.00 1.16 1.99 0 0 (Gen: 1)
"performed!"
39464 2200 1058952 0.00 0.00 1.16 1.99 0 0 (Gen: 1)
22264 1560 1075992 0.00 0.00 1.16 2.00 0 0 (Gen: 0)
0 0.00 0.00
Así que después de GC todavía hay 1M en el montón (sin -G1) Con.. - G1 veo:.
34340656 20520040 20524800 0.10 0.12 0.76 0.85 0 0 (Gen: 0)
41697072 24917800 24922560 0.12 0.14 0.91 1.01 0 0 (Gen: 0)
70790776 800 2081568 0.00 0.02 1.04 1.20 0 0 (Gen: 0)
0 800 2081568 0.00 0.00 1.04 1.20 0 0 (Gen: 0)
"performed!"
39464 2184 1058952 0.00 0.00 1.05 1.21 0 0 (Gen: 0)
22264 2856 43784 0.00 0.00 1.05 1.21 0 0 (Gen: 0)
0 0.00 0.00
Así aproximadamente 2 M Este es el x86_64/Linux
Vamos a pensar en the STG machine storage model para ver si hay algo. más en el montón.
cosas que podrían ser en ese 1M del espacio:
- CAF para cosas como
[]
, las constantes de cadena, y el pequeño Int
y Char
piscina, además de las cosas en las bibliotecas, la stdin
MVar?
- Thread State Objects (TSO) para el subproceso
main
.
- Cualquier manejador de señal asignado.
- El administrador de IO código Haskell.
- chispas en la piscina chispa
Por experiencia, esta cifra ligeramente inferior a 1 M parece ser la "huella" por defecto de un binario GHC. Eso es lo que también he visto en otros programas (por ejemplo, las huellas más pequeñas del programa de tiroteos nunca son inferiores a 900K).
Quizás el generador de perfiles puede decir algo.Aquí está la -hT
perfil (no hay bibliotecas de perfiles necesarios), después de insertar un bucle ocupado mínimo al final de la cadena a cabo la cola:
$ ./A +RTS -K10M -S -hT -i0.001
Los resultados en este gráfico:
Victory! ¡Mira ese ~ 1M objeto de pila de hilos ahí!
No conozco una forma de reducir los TSO.
El código que produce el gráfico anterior:
import Language.Haskell.Exts.Annotated -- from haskell-src-exts
import System.Mem
import System.IO
import Data.Int
import Control.Exception
main :: IO()
main = do
evaluate $ length $ show $ fromParseResult
$ parseFileContents
$ "data C = C {a :: F {- " ++ replicate 400000 'd' ++ " -} }"
performGC
performGC
print "performed!"
performGC
-- busy loop so we can sample what's left on the heap.
let go :: Int32 -> IO()
go 0 = return()
go n = go $! n-1
go (maxBound :: Int32)
Soy consciente de que esto es un comentario totalmente inútil, pero que realmente me gusta ver a preguntas aquí de personas que saben mucho más acerca de Haskell que yo, porque las respuestas que siguen tienden a ser completamente fascinantes. :] –
Bueno, es un cambio agradable del flujo constante de preguntas que responden por "do not, pero' insafePerformIO' "," 'fromIntegral'" y "convertir pestañas en espacios" ... – yatima2975