PRB: No se puede descargar los ensamblados que se crean y se carga mediante el uso de secuencias de comandos en XSLT

Seleccione idioma Seleccione idioma
Id. de artículo: 316775 - Ver los productos a los que se aplica este artículo
Este artículo se ha archivado. Se ofrece "tal cual" y no se volverá a actualizar.
En este artículo se refiere a la siguiente de Microsoft.NET Framework Class Library espacios de nombres:
  • System.IO
  • System.Xml
  • System.Xml.XPath
  • System.Xml.xsl
Expandir todo | Contraer todo

En esta página

Síntomas

Cuando utilice el elemento de <msxsl:script> varias veces con el marco de trabajo de System.Xml.Xslt, puede producir una pérdida de memoria con un gran volumen de aplicación de lenguaje de marcado Extensible (XML) o lenguaje de hoja de estilos Extensible (XSL). </msxsl:script>

Causa

Las clases de la System.Xml espacio de nombres admite el uso de secuencias de comandos incrustadas mediante el elemento de secuencia de comandos en aplicaciones de transformación XSL (XSLT). Por lo tanto, el elemento <msxsl:script> le permite elegir el lenguaje de programación (como Microsoft Visual C#.NET o Microsoft Visual Basic.(NET) para realizar determinadas tareas.</msxsl:script>

Las funciones declaradas dentro de bloques de secuencias de comandos. Cuando se utiliza la secuencia de comandos incrustada con un archivo XSL, un ensamblado que contiene lenguaje intermedio de Microsoft (MSIL) creado y cargado en memoria. Debido a una limitación de diseño de esta versión de Microsoft.NET Framework, no se puede descargar dicho ensamblado de la memoria. Esto puede causar una pérdida de memoria si los ensamblados se crean y se cargan varias veces o en un bucle.

Solución

Para resolver este problema, no repetidamente cargue el XSLT con la secuencia de comandos. Desarrollar la aplicación de modo que la transformación XSL de carga una vez y reutilizar tantas veces como sea necesario. Esta práctica también mejora el rendimiento.

Por ejemplo, el código siguiente pérdidas de memoria:
For(int i=0;i<1000;i++)
{
      xslt.Load(stylesheet);
      //Do other stuff
      xslt.Transform(doc, null, writer);
}
				
Cambie el código siguiente para cargar XSLT sólo una vez y volver a utilizarlo en un bucle:
xslt.Load(stylesheet);
For(int i=0;i<1000;i++)
{

      //Do other stuff
      xslt.Transform(doc, null, writer);
}
				
Este código sólo carga el ensamblado de una vez y no pierda memoria.

Solución

Descargar un ensamblado individual por descarga todos los dominios de aplicación que contienen el ensamblado. Para ello, llame a la AppDomain.Unload() método para cada dominio de aplicación que tiene el ensamblado cargado o llamada a la UnloadDomain() método de la API de alojamiento no administrada.

Más información

Pasos para reproducir el comportamiento

  1. Crear una aplicación de Visual C#.Proyecto de aplicación de consola de red.
  2. Crear una aplicación XSLT y, a continuación, agregue el código siguiente:
    using System;
    using System.IO;
    using System.Xml;
    using System.Xml.XPath;
    using System.Xml.Xsl;
    
    public class Sample
    {
    	private const String filename = "..\\..\\XmlFile1.xml";
    	private const String stylesheet = "..\\..\\XSLTFile1.xslt";
    
    	public static void Main() 
    	{
    
                    for(int i=0;i<1000;i++)
                    {
    
    		XslTransform xslt = new XslTransform();
                    xslt.Load(stylesheet);
    
    		//Load the XML data file.
    		XPathDocument doc = new XPathDocument(filename);
    
    		//Create an XmlTextWriter to write to the console.         
    		XmlTextWriter writer = new XmlTextWriter(Console.Out);
    		writer.Formatting = Formatting.Indented;
    
    		//Transform the file.
    		xslt.Transform(doc, null, writer);
    		writer.Close();
                    }
    		System.Console.Read();
            
    	} 
    }
    					
  3. Crear un archivo XSLT que se denomina XSLTFile1.xslt y, a continuación, agregue el código siguiente:
     <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
        xmlns:msxsl="urn:schemas-microsoft-com:xslt"
        xmlns:user="urn:my-scripts">
    
      <msxsl:script language="C#" implements-prefix="user">
    
    <![CDATA[
    
         public double circumference(double radius){
           double pi = 3.14;
           double circ = pi*radius*2;
           return circ;
         }      
                ]] >     
    <!-- Remove the space between ]] and > in the preceding line. -->
    <!-- The space is inserted because of a publishing constraint. -->
    
       </msxsl:script>
    
      <xsl:template match="data">  
      <circles>
    
      <xsl:for-each select="circle">
        <circle>
        <xsl:copy-of select="node()"/>
           <circumference>
              <xsl:value-of select="user:circumference(radius)"/>        
           </circumference>
        </circle>
      </xsl:for-each>
      </circles>
      </xsl:template>
    </xsl:stylesheet>
    					
  4. Crear un archivo XML denominado XMLFile1.xml y, a continuación, agregue el código siguiente:
    <?xml version='1.0'?>
    <data>
      <circle>
        <radius>12</radius>
      </circle>
      <circle>
        <radius>37.5</radius>
      </circle>
    </data>
    					
  5. Guarde los archivos XML y XSL en la carpeta de aplicación.
  6. Recorra el código. Observe que los ensamblados se crean y se carga en la ventana de resultados de Visual Studio.NET.
  7. Abra el Monitor de rendimiento. Observe que el número de bytes privado muestra el aumento en la memoria.

Propiedades

Id. de artículo: 316775 - Última revisión: lunes, 24 de febrero de 2014 - Versión: 1.0
La información de este artículo se refiere a:
  • Microsoft .NET Framework 4.0
  • Microsoft .NET Framework 2.0
  • Microsoft .NET Framework 1.0
Palabras clave: 
kbnosurvey kbarchive kbprb kbmt KB316775 KbMtes
Traducción automática
IMPORTANTE: Este artículo ha sido traducido por un software de traducción automática de Microsoft (http://support.microsoft.com/gp/mtdetails) en lugar de un traductor humano. Microsoft le ofrece artículos traducidos por un traductor humano y artículos traducidos automáticamente para que tenga acceso en su propio idioma a todos los artículos de nuestra base de conocimientos (Knowledge Base). Sin embargo, los artículos traducidos automáticamente pueden contener errores en el vocabulario, la sintaxis o la gramática, como los que un extranjero podría cometer al hablar el idioma. Microsoft no se hace responsable de cualquier imprecisión, error o daño ocasionado por una mala traducción del contenido o como consecuencia de su utilización por nuestros clientes. Microsoft suele actualizar el software de traducción frecuentemente.
Haga clic aquí para ver el artículo original (en inglés): 316775

Contact us for more help

Contact us for more help
Connect with Answer Desk for expert help.
Get more support from smallbusiness.support.microsoft.com