2010-08-05 16 views
21

¿Hay alguna manera de perfilar el uso de la memoria de mathkernel (hasta variables individuales) que no sea el pago $$$ por su plugin Eclipse (mathematica workbench, iirc)?Uso de la memoria de generación de perfiles en Mathematica

Ahora mismo termino la ejecución de un programa que requiere varios GB de memoria RAM, pero las únicas cosas que se almacenan deben ser ~ 50MB de datos como máximo, aunque mathkernel.exe tiende a aferrarse a ~ 1.5GB (básicamente, como tanto como Windows lo dará). ¿Hay alguna forma mejor de evitar esto, aparte de guardar los datos que necesito y salir del kernel todo el tiempo?

EDIT: Acabo de enterarme de la función ByteCount (que muestra algunos resultados perturbadores en los tipos de datos básicos, pero eso es además del punto), pero incluso la suma de todas mis variables no está cerca de la cantidad tomada por mathkernel. ¿Lo que da?

Respuesta

12

Una cosa que muchos usuarios no se dan cuenta es que se necesita memoria para almacenar todas sus entradas y salidas en los símbolos In y Out, independientemente de si asigna una salida a una variable. Out también tiene un alias de %, donde % es la salida anterior, %% es el penúltimo, etc. %123 es equivalente a Out[123].

Si usted no tiene el hábito de usar %, o lo utiliza solamente a unos niveles de profundidad, establecer $HistoryLength a 0 o un pequeño número entero positivo, para mantener sólo el último pocos (o ningún) emite alrededor de Out .

Es posible que también desee consultar las funciones MaxMemoryUsed y MemoryInUse.

Por supuesto, el problema $HistoryLength puede ser o no su problema, pero no ha compartido cuál es su evaluación real. Si puede publicarlo, tal vez alguien pueda arrojar más luz sobre por qué es tan intensivo en memoria.

4

Michael Pilat's answer es bueno, y MemoryInUse y MaxMemoryUsed son probablemente las mejores herramientas que tiene. ByteCount raramente es muy útil porque lo que mide puede ser una gran sobreestimación porque ignora las subexpresiones compartidas y a menudo ignora la memoria a la que no se puede acceder directamente a través de las funciones de Mathematica, que a menudo es un componente principal del uso de la memoria.

Una cosa que puede hacer en algunas circunstancias es usar la función Share, que fuerza a las subexpresiones a ser compartidas cuando sea posible. En algunas circunstancias, esto puede ahorrarle decenas o incluso cientos de magabytes. Puede decir qué tan bien está funcionando usando MemoryInUse antes y después de usar Share.

Además, algunas cosas inofensivas pueden hacer que Mathematica use mucha más memoria de la esperada. Las matrices contiguas de los reales de la máquina (y solo reales de la máquina) se pueden asignar como matrices llamadas "empacadas", de forma muy similar a las asignadas por C o Fortran. Sin embargo, si tiene una combinación de máquinas reales y otras estructuras (incluidos símbolos) en una matriz, todo tiene que ser "boxed", y la matriz se convierte en una matriz de punteros, lo que puede agregar muchos sobrecargas.

2

Una forma es automatizar el reinicio del kernel cuando se queda sin memoria. Puede ejecutar su código que consume memoria en un kernel esclavo, mientras que el kernel maestro solo toma el resultado del cálculo y controla el uso de la memoria.

+0

@Alexy, que puede apuntar a un código de ejemplo/demostración? –

+0

@myaccount_ram Ejemplo: http://stackoverflow.com/a/5017071/590388 –

7

Aquí está mi solución para perfiles de uso de la memoria:

myByteCount[symbolName_String] := 
    Replace[ToHeldExpression[symbolName], 
    Hold[x__] :> 
    If[MemberQ[Attributes[x], Protected | ReadProtected], 
    Sequence @@ {}, {ByteCount[ 
     Through[{OwnValues, DownValues, UpValues, SubValues, 
      DefaultValues, FormatValues, NValues}[[email protected], 
     Sort -> False]]], symbolName}]]; 

With[{listing = myByteCount /@ Names[]}, 
Labeled[Grid[[email protected][Sort[listing], -100], Frame -> True, 
    Alignment -> Left], 
    Column[{Style[ 
    "ByteCount for symbols without attributes Protected and \ 
ReadProtected in all contexts", 16, FontFamily -> "Times"], 
    Style[[email protected]{"Total: ", Total[listing[[All, 1]]], " bytes for ", 
     Length[listing], " symbols"}, Bold]}, Center, 1.5], Top]] 

Evaluación del anterior muestra el siguiente cuadro:

screenshot

+0

En 7.0.1 aparece el error: '' Opcional :: opdef: el valor predeterminado para el argumento opcional BoxForm'pat _: {_, __ } contiene un patrón. >> '' pero también obtengo resultados. ¿Recibes el error también? –

+0

@ Mr.Wizard En la sesión nueva no los consigo, pero después de un cierto trabajo, el código anterior comienza a producir estos mensajes. –

Cuestiones relacionadas