<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" media="screen" href="/~d/styles/rss2full.xsl"?><?xml-stylesheet type="text/css" media="screen" href="http://feeds.feedburner.com/~d/styles/itemcontent.css"?><rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" version="2.0"><channel><title>Pensando en asíncrono</title><link>http://geeks.ms/blogs/vtortola/default.aspx</link><description>Estudiando el desarrollo multithreading y .NET en general</description><dc:language /><generator>CommunityServer 2008.5 SP1 (Build: 31106.3070)</generator><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" type="application/rss+xml" href="http://feeds.feedburner.com/PensandoEnAsncrono" /><feedburner:info xmlns:feedburner="http://rssnamespace.org/feedburner/ext/1.0" uri="pensandoenasncrono" /><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="hub" href="http://pubsubhubbub.appspot.com/" /><item><title>Integrar un video de YouTube en Silverlight 2</title><link>http://geeks.ms/blogs/vtortola/archive/2009/05/17/integrar-un-video-de-youtube-en-silverlight-2.aspx</link><pubDate>Sun, 17 May 2009 20:04:00 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:148802</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>0</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=148802</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2009/05/17/integrar-un-video-de-youtube-en-silverlight-2.aspx#comments</comments><description>&lt;p&gt;&lt;a href="http://geeks.ms/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/vtortola/silveryoutubemini_5F00_1.jpg"&gt;&lt;img style="border-top-width:0px;border-left-width:0px;border-bottom-width:0px;margin:0px 35px 0px 0px;border-right-width:0px;" alt="silveryoutubemini" src="http://geeks.ms/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/vtortola/silveryoutubemini_5F00_thumb_5F00_1.jpg" align="left" border="0" /&gt;&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;&amp;nbsp;Me pareci&amp;oacute; tan curioso que me decid&amp;iacute; a probarlo :D Es sabido, que no se puede insertar un componente Flash en Silverlight 2 ... pero&amp;nbsp;como comenta&amp;nbsp;&lt;a href="http://weblogs.manas.com.ar/ary"&gt;Ary Boretc&lt;/a&gt; se puede &lt;a href="http://weblogs.manas.com.ar/ary/2008/09/11/embedding-youtube-videos-in-silverlight/"&gt;meter en un DIV flotante&lt;/a&gt; y colocarlo en&amp;nbsp;la pantalla. Funciona bastante bien, aunque no funciona a pantalla completa (ya que en pantalla completa solo se puede ver la aplicaci&amp;oacute;n Silverlight) y tampoco funciona en Internet Explorer, intentar&amp;eacute; averiguar porque :P&lt;/p&gt;
&lt;p&gt;Me faltaba entonces poder moverlo a voluntad como si fuese un elemento m&amp;aacute;s en mi &lt;a href="http://silverlight.vtortola.net/"&gt;emulador de escritorio&lt;/a&gt;. El control que Ary propone, tiene unas propiedades para controlar la posici&amp;oacute;n y el tama&amp;ntilde;o asi que simplemente es cuesti&amp;oacute;n de &amp;quot;atar&amp;quot; el div al contenido de la ventana, todo gracias a &lt;a href="http://msdn.microsoft.com/en-us/library/system.windows.uielement.transformtovisual(VS.95).aspx"&gt;TransformToVisual()&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;Cada ventana es un &lt;i&gt;UserControl&lt;/i&gt; que acepta otro parametro como &lt;i&gt;Content&lt;/i&gt; , asi que debia hacer que en todo momento el div ocupase la superficie de ese &lt;i&gt;Content&lt;/i&gt;, tanto al moverlo como al redimensionarlo; aunque son elementos de mundos distintos, bailan sobre la misma superficie, un &lt;i&gt;Canvas&lt;/i&gt; (en este caso una clase derivada), asi que simplemente se trata de obtener las coordenadas absolutas del Content con respecto al &lt;i&gt;Canvas&lt;/i&gt; y aplicarselas al DIV flotante para controlar su posici&amp;oacute;n, adem&amp;aacute;s de controlar tambi&amp;eacute;n el tama&amp;ntilde;o, que ha de ser el mismo.&lt;/p&gt;
&lt;p&gt;Lo primero creo un &lt;i&gt;UserControl&lt;/i&gt; que ser&amp;aacute; el contenedor virtual del video (digo virtual, porque realmente no contiene nada :P), y este control inicializa el control &lt;i&gt;YouTubePlayer&lt;/i&gt; de Ary.&lt;/p&gt;
&lt;p&gt;Siguiente, necesito acceder a la ventana para que me informe cada vez que el layout cambia. Creo que no hay una forma dada para escalar en el arbol visual buscando un Parent espec&amp;iacute;fico; yo cree un m&amp;eacute;todo extensor para este fin:&lt;/p&gt;
&lt;div class="csharpcode"&gt;
&lt;pre class="alt"&gt;&lt;span class="kwrd"&gt;public&lt;/span&gt; &lt;span class="kwrd"&gt;static&lt;/span&gt; T GetParent&amp;lt;T&amp;gt;(&lt;span class="kwrd"&gt;this&lt;/span&gt; FrameworkElement element)&lt;/pre&gt;
&lt;pre&gt;    &lt;span class="kwrd"&gt;where&lt;/span&gt; T : FrameworkElement&lt;/pre&gt;
&lt;pre class="alt"&gt;{&lt;/pre&gt;
&lt;pre&gt;    &lt;span class="kwrd"&gt;while&lt;/span&gt; (element.Parent != &lt;span class="kwrd"&gt;null&lt;/span&gt;)&lt;/pre&gt;
&lt;pre class="alt"&gt;    {&lt;/pre&gt;
&lt;pre&gt;        &lt;span class="kwrd"&gt;if&lt;/span&gt; (element.Parent &lt;span class="kwrd"&gt;is&lt;/span&gt; T)&lt;/pre&gt;
&lt;pre class="alt"&gt;            &lt;span class="kwrd"&gt;return&lt;/span&gt; (T)element.Parent;&lt;/pre&gt;
&lt;pre&gt;        &lt;span class="kwrd"&gt;else&lt;/span&gt;&lt;/pre&gt;
&lt;pre class="alt"&gt;            element = element.Parent &lt;span class="kwrd"&gt;as&lt;/span&gt; FrameworkElement;&lt;/pre&gt;
&lt;pre&gt;    }&lt;/pre&gt;
&lt;pre class="alt"&gt;    &lt;span class="kwrd"&gt;return&lt;/span&gt; &lt;span class="kwrd"&gt;null&lt;/span&gt;;&lt;/pre&gt;
&lt;pre&gt;}&lt;/pre&gt;
&lt;/div&gt;
&lt;p&gt;Una vez tengo el objeto ventana que contiene my &lt;i&gt;UserContorl&lt;/i&gt; me subscribo a su evento &lt;a href="http://msdn.microsoft.com/en-us/library/system.windows.frameworkelement.layoutupdated(VS.95).aspx"&gt;LayoutUpdated&lt;/a&gt;. Este m&amp;eacute;todo extensor me vale tambi&amp;eacute;n para encontrar el &lt;i&gt;Canvas&lt;/i&gt; donde &amp;quot;bailan&amp;quot; los elementos, para poder obtener la posici&amp;oacute;n relativa a este. Cada vez que la ventana se redimensione, se dispara el evento &lt;i&gt;LayoutUpdated&lt;/i&gt;, pero no cuando se mueve, ya que lo que estoy modificando son las propiedades asociadas &lt;i&gt;Canvas.Top&lt;/i&gt; y &lt;i&gt;Canvas.Left&lt;/i&gt;, asi que me asegurar&amp;eacute; de que cada vez que se mueve la ventana se llame a &lt;a href="http://msdn.microsoft.com/en-us/library/system.windows.uielement.invalidatemeasure.aspx"&gt;InvalidateMeasure()&lt;/a&gt; para se dispare el citado evento.&lt;/p&gt;
&lt;p&gt;Ahora, en el manejador del evento &lt;i&gt;LayoutUpdated&lt;/i&gt; que nos subscribimos, hay que actualizar la posici&amp;oacute;n del DIV flotante cada vez que la ventana cambia. Dentro de mi &lt;i&gt;UserControl&lt;/i&gt;, hay un control de tipo &lt;i&gt;ContentControl&lt;/i&gt;&amp;nbsp; que he llamado&amp;nbsp;&lt;i&gt;YTContainer&lt;/i&gt;, que es donde el video deber&amp;aacute; aparecer.&amp;nbsp;&amp;nbsp;Gracias a &lt;a href="http://msdn.microsoft.com/en-us/library/system.windows.uielement.transformtovisual(VS.95).aspx"&gt;TransformToVisual()&lt;/a&gt; podemos obtener cual es la posici&amp;oacute;n relativa a un control de cualquiera de sus descendientes, aunque no sean descendientes directos, como es el caso (hay toda una jerarquia de &lt;i&gt;Grids&lt;/i&gt;, ventanas y &lt;i&gt;UserControl&lt;/i&gt; desde &lt;i&gt;YTContainer&lt;/i&gt; al &lt;i&gt;Canvas&lt;/i&gt;):&lt;/p&gt;
&lt;div class="csharpcode"&gt;
&lt;pre class="alt"&gt;Point position = YTContainer.TransformToVisual(surface)&lt;/pre&gt;
&lt;pre&gt;                           .Transform(&lt;span class="kwrd"&gt;new&lt;/span&gt; Point(0, 0));&lt;/pre&gt;
&lt;pre class="alt"&gt;&amp;nbsp;&lt;/pre&gt;
&lt;pre&gt;player.Top = position.Y;&lt;/pre&gt;
&lt;pre class="alt"&gt;player.Left = position.X;&lt;/pre&gt;
&lt;pre&gt;player.Width = YTContainer.ActualWidth;&lt;/pre&gt;
&lt;pre class="alt"&gt;player.Height = YTContainer.ActualHeight;&lt;/pre&gt;
&lt;/div&gt;
&lt;p&gt;&amp;nbsp;De esa forma se que punto en el &lt;i&gt;Canvas&lt;/i&gt; se corresponde con el punto relativo &amp;quot;0,0&amp;quot; de &lt;i&gt;YTContainer,&lt;/i&gt; ya simplemente tengo que actualizar las propiedades del &lt;i&gt;YoutubePlayer&lt;/i&gt;&lt;/p&gt;
&lt;p&gt;Y nada m&amp;aacute;s, se puede ver el resultado en &lt;a href="http://silverlight.vtortola.net/"&gt;mi emulador de escritorio&lt;/a&gt;. Investigar&amp;eacute; porque no funciona en Internet Explorer.&lt;/p&gt;
&lt;p&gt;Creo que tambi&amp;eacute;n se puede hacer usando propiedades de dependencia y data binding...&amp;nbsp;&amp;nbsp;&lt;/p&gt;
&lt;h5&gt;&lt;a href="http://vtortola.net/post/Integrar-un-video-de-YouTube-en-Silverlight-2.aspx"&gt;Integrar un video de YouTube en Silverlight 2| vtortola.NET&lt;/a&gt;&lt;/h5&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=148802" width="1" height="1"&gt;</description><category domain="http://geeks.ms/blogs/vtortola/archive/tags/C_2300_+3.0/default.aspx">C# 3.0</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/.NET+3.5/default.aspx">.NET 3.5</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/Silverlight/default.aspx">Silverlight</category></item><item><title>Gestor de ventanas (Window Manager) en Silverlight 2</title><link>http://geeks.ms/blogs/vtortola/archive/2009/02/08/gestor-de-ventanas-window-manager-en-silverlight-2.aspx</link><pubDate>Sun, 08 Feb 2009 20:33:00 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:142309</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>5</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=142309</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2009/02/08/gestor-de-ventanas-window-manager-en-silverlight-2.aspx#comments</comments><description>&lt;p&gt;&lt;a href="http://geeks.ms/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/vtortola/silverwindow.jpg"&gt;&lt;img style="border-top-width:0px;border-left-width:0px;border-bottom-width:0px;margin:0px 15px 0px 0px;border-right-width:0px;" alt="silverwindow" src="http://geeks.ms/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/vtortola/silverwindow_5F00_thumb.jpg" align="left" border="0" /&gt;&lt;/a&gt; He creado un peque&amp;ntilde;o &lt;a href="http://es.wikipedia.org/wiki/Gestor_de_ventanas"&gt;gestor de ventanas&lt;/a&gt; como&amp;nbsp;libreria&amp;nbsp;para &lt;a href="http://silverlight.net/"&gt;Silverlight 2&lt;/a&gt;, que permite a&amp;ntilde;adir cualquier FrameworkElement embebido en una ventana, que se puede mover (desde la barra de t&amp;iacute;tulo), redimensionar (desde la esquina inferior derecha), &amp;nbsp;colapsar (bot&amp;oacute;n _) y&amp;nbsp;cerrar (bot&amp;oacute;n X). Adem&amp;aacute;s las ventanas pueden ser ordenadas en cascada &amp;oacute; en mosaico.&lt;/p&gt;
&lt;p&gt;La clase se llama &lt;i&gt;SilverWindowManager&lt;/i&gt;, hereda de &lt;i&gt;Canvas&lt;/i&gt;, y lo que hace es crear unos elementos llamados &lt;i&gt;SilverWindow&lt;/i&gt;, que son &lt;i&gt;UserControl&lt;/i&gt;, y conectar 5 eventos entre ventana y escritorio, dos del &amp;quot;escritorio&amp;quot; a la ventana para que se puedan realizar las acciones de mover y redimensionar, y 3 de la ventana al escritorio para informar cuando se activa &amp;oacute; cierra una ventana. &lt;i&gt;SilverWindow&lt;/i&gt; usa el &lt;i&gt;FrameworkElement&lt;/i&gt; que se le pasa en el constructor para rellenar su espacio de trabajo. Cualquier &lt;i&gt;FrameworkElement&lt;/i&gt; es bueno, desde por ejemplo &lt;i&gt;MediaElement&lt;/i&gt; para poner un video, como un &lt;i&gt;UserControl&lt;/i&gt;, de hecho lo que este ejemplo abre cada vez es una nueva instancia de un &lt;i&gt;UserControl&lt;/i&gt; llamado &lt;i&gt;DummyUserCtrl&lt;/i&gt; que tiene un color de fondo aleatorio.&lt;/p&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Se puede ver en este enlace : &lt;a href="http://www.vtortola.net/silverlight2/windowmanager.html"&gt;&lt;b&gt;Gestor de Ventanas Silverlight&lt;/b&gt;&lt;/a&gt;. (Los videos son de silverlight.net y tardan un poco en cargar :P)  &lt;/li&gt;
&lt;li&gt;He subido la soluci&amp;oacute;n tambi&amp;eacute;n: &lt;a href="http://www.vtortola.net/silverlight2/WMS2_Test.zip"&gt;C&amp;oacute;digo fuente&lt;/a&gt;.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Hay una cosa con la que no estoy muy contento, y es el comportamiento de redimensionar, primero porque parece que redimensiona a menos velocidad de la que se mueve el puntero y no consigo ver por que, y segundo porque al moverse el puntero fuera de la zona de redimensionamiento mientras esta redimensionando, hace que el evento MouseLeftButtonUp pase en cualquier sitio... y al ser incomprensiblemente de tipo &lt;i&gt;Direct&lt;/i&gt; en lugar de &lt;i&gt;Bubbling &lt;/i&gt;(su hom&amp;oacute;logo en WPF tambi&amp;eacute;n es &lt;i&gt;Direct&lt;/i&gt;, pero adem&amp;aacute;s tiene un &lt;i&gt;MouseUp&lt;/i&gt; de tipo &lt;i&gt;Bubbling&lt;/i&gt;), si se libera sobre un TextBox &amp;oacute; Bot&amp;oacute;n parece que se queda la acci&amp;oacute;n enganchada hasta el siguiente &amp;quot;mouse up&amp;quot; porque el evento se corta en ese control. Asi que si alguien le echa un vistazo al c&amp;oacute;digo y ve el porque de estos problemas... le estaria muy agradecido si me lo dice :D&lt;/p&gt;
&lt;p&gt;El dise&amp;ntilde;o no es muy all&amp;aacute;, pero es que ni&amp;nbsp;todav&amp;iacute;a me he puesto a utilizar &lt;i&gt;Expression Blend 2&lt;/i&gt;... ni todav&amp;iacute;a estoy muy puesto en cuestiones de dise&amp;ntilde;o gr&amp;aacute;fico :D&lt;/p&gt;
&lt;p&gt;Esta es mi 4&amp;ordm; experimento con Silvelight 2, y la verdad es que esta bastante limitado con respecto a su hermano mayor WPF(con el que batallo dia a dia), se echan mucho&amp;nbsp;de menos los estilos impl&amp;iacute;citos, los&amp;nbsp;triggers, las&amp;nbsp;opciones de databinding como ElementName y RelativeSource,&amp;nbsp;la distribuci&amp;oacute;n de eventos, el bot&amp;oacute;n derecho y central del rat&amp;oacute;n... los triggers... y supongo que habr&amp;aacute; m&amp;aacute;s cosas que no est&amp;aacute;n... ya los ir&amp;eacute; echando en falta :P Pero bien lo vale por lo peque&amp;ntilde;o que es el runtime,&amp;nbsp;me gusta bastante :D&lt;/p&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;h5&gt;&lt;a href="http://vtortola.net/post/Gestor-de-ventanas-%28Window-Manager%29-en-Silverlight-2.aspx"&gt;Gestor de ventanas (Window Manager) en Silverlight 2 | vtortola.NET&lt;/a&gt;&lt;/h5&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=142309" width="1" height="1"&gt;</description><category domain="http://geeks.ms/blogs/vtortola/archive/tags/Silverlight/default.aspx">Silverlight</category></item><item><title>Ordenaciones personalizadas con LINQ</title><link>http://geeks.ms/blogs/vtortola/archive/2008/09/12/ordenaciones-personalizadas-con-linq.aspx</link><pubDate>Fri, 12 Sep 2008 21:55:06 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:98541</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>2</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=98541</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2008/09/12/ordenaciones-personalizadas-con-linq.aspx#comments</comments><description>&lt;p&gt;Esta mañana necesitaba &lt;a href="http://msdn.microsoft.com/en-us/vcsharp/aa336756.aspx"&gt;ordenar&lt;/a&gt; los elementos de una tabla en función de uno de los campos, pero el problema era que la comparación no era alfabética ni similar,&amp;nbsp;era en función de unos criterios propios; uno de los parámetros que aceptan los métodos extensores &lt;em&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/system.linq.enumerable.orderby.aspx"&gt;OrderBy&lt;/a&gt;&lt;/em&gt;, &lt;em&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/system.linq.enumerable.orderbydescending.aspx"&gt;OrderByDescending&lt;/a&gt;&lt;/em&gt;, &lt;em&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/system.linq.enumerable.thenby.aspx"&gt;ThenBy&lt;/a&gt;&lt;/em&gt; and &lt;em&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/system.linq.enumerable.thenbydescending.aspx"&gt;ThenByDescending&lt;/a&gt;&lt;/em&gt; es un &lt;a href="http://msdn.microsoft.com/en-us/vcsharp/aa336756.aspx"&gt;IComparer&amp;lt;&amp;gt;&lt;/a&gt;, probé y funcionó, asignaba un peso a cada valor y luego comparaba en el método &lt;a href="http://msdn.microsoft.com/en-us/vcsharp/aa336756.aspx"&gt;Compare&lt;/a&gt;&amp;nbsp;los pesos de los dos parámetros de entrada,&amp;nbsp;pero aún asi no me gustaba como quedaba, no me gustaba lo de tener que escribir una clase solo para este propósito... buscaba algo más... compacto...&amp;nbsp;asi que con ayuda de mi compañero&amp;nbsp;use un delegado anónimo primero que directamente&amp;nbsp;devolvia el peso&amp;nbsp;en &lt;strong&gt;TKey&lt;/strong&gt; inferido como &lt;em&gt;Int32&lt;/em&gt;, que es en lo que LINQ basaria la ordenación&amp;nbsp;y luego lo substituí por una expresión lambda; es realmente interesante como LINQ te facilita la vida :D&lt;/p&gt; &lt;p&gt;Este pequeño ejemplo ordena un &lt;em&gt;DataTable&lt;/em&gt; en función de su columna &lt;em&gt;&amp;quot;Country&amp;quot;&lt;/em&gt; asignando a cada valor un peso en &lt;em&gt;Int32&lt;/em&gt;&amp;nbsp;y siendo este peso el que devuelve&amp;nbsp;la expresión infiriendo&amp;nbsp;&lt;strong&gt;TKey&lt;/strong&gt; como &lt;em&gt;Int32&lt;/em&gt;, que será en lo que LINQ base ordenación de los elementos. Anotar que el elemento que queramos que tenga más relevancia debe ser el de menos peso y el que menos el que más peso:&lt;/p&gt; &lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;DataTable EmployeesByCountry = &lt;/pre&gt;&lt;pre&gt;            EmployeesTable.AsEnumerable()&lt;/pre&gt;&lt;pre class="alt"&gt;            &lt;span class="rem"&gt;//.OrderBy(delegate(DataRow Employee)&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;            .OrderBy(Employee =&amp;gt;&lt;/pre&gt;&lt;pre class="alt"&gt;                {&lt;/pre&gt;&lt;pre&gt;                    &lt;span class="kwrd"&gt;switch&lt;/span&gt;(Employee.Field&amp;lt;String&amp;gt;(&lt;span class="str"&gt;&amp;quot;Country&amp;quot;&lt;/span&gt;))&lt;/pre&gt;&lt;pre class="alt"&gt;                    {&lt;/pre&gt;&lt;pre&gt;                        &lt;span class="kwrd"&gt;case&lt;/span&gt; &lt;span class="str"&gt;&amp;quot;Denmark&amp;quot;&lt;/span&gt;:&lt;span class="kwrd"&gt;return&lt;/span&gt; 3;&lt;/pre&gt;&lt;pre class="alt"&gt;                        &lt;span class="kwrd"&gt;case&lt;/span&gt; &lt;span class="str"&gt;&amp;quot;France&amp;quot;&lt;/span&gt;:&lt;span class="kwrd"&gt;return&lt;/span&gt; 2;&lt;/pre&gt;&lt;pre&gt;                        &lt;span class="kwrd"&gt;case&lt;/span&gt; &lt;span class="str"&gt;&amp;quot;Ireland&amp;quot;&lt;/span&gt;:&lt;span class="kwrd"&gt;return&lt;/span&gt; 4;&lt;/pre&gt;&lt;pre class="alt"&gt;                        &lt;span class="kwrd"&gt;case&lt;/span&gt; &lt;span class="str"&gt;&amp;quot;Spain&amp;quot;&lt;/span&gt;:&lt;span class="kwrd"&gt;return&lt;/span&gt; 1;&lt;/pre&gt;&lt;pre&gt;                        &lt;span class="kwrd"&gt;case&lt;/span&gt; &lt;span class="str"&gt;&amp;quot;UK&amp;quot;&lt;/span&gt;:&lt;span class="kwrd"&gt;return&lt;/span&gt; 5;&lt;/pre&gt;&lt;pre class="alt"&gt;                        &lt;span class="kwrd"&gt;default&lt;/span&gt;: &lt;span class="kwrd"&gt;return&lt;/span&gt; Int32.MaxValue;&lt;/pre&gt;&lt;pre&gt;                    }&lt;/pre&gt;&lt;pre class="alt"&gt;                }).CopyToDataTable();&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Aún así estoy&amp;nbsp;seguro que habrá formas&amp;nbsp;mejores y más sencillas de hacerlo.&amp;nbsp;Evidentemente es mejor si tenemos un algorritmo que calcule el peso&amp;nbsp;en lugar de tener que fijarlos &amp;quot;a capón&amp;quot; ... pero hay situaciones... que no hay más remedio :D&lt;/p&gt;
&lt;h5&gt;&lt;a href="http://vtortola.net/post/Ordenaciones-personalizadas-con-LINQ.aspx"&gt;Ordenaciones personalizadas con LINQ| vtortola.NET&lt;/a&gt;&lt;/h5&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=98541" width="1" height="1"&gt;</description><category domain="http://geeks.ms/blogs/vtortola/archive/tags/C_2300_+3.0/default.aspx">C# 3.0</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/.NET+3.5/default.aspx">.NET 3.5</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/LINQ/default.aspx">LINQ</category></item><item><title>Update-Select en un DataTable con LINQ</title><link>http://geeks.ms/blogs/vtortola/archive/2008/09/12/update-select-en-un-datatable-con-linq.aspx</link><pubDate>Thu, 11 Sep 2008 22:33:20 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:98435</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>3</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=98435</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2008/09/12/update-select-en-un-datatable-con-linq.aspx#comments</comments><description>&lt;p&gt;Últimamente ya no escribo nada, estoy totalmente inmerso en el mundo LINQ con el&amp;nbsp;&lt;a href="http://shop.campusmvp.com/Product-C-3.0-y-LINQ_1.aspx"&gt;C# 3.0 y LINQ&lt;/a&gt;&amp;nbsp;de Octavio Hernandez&amp;nbsp;y el &lt;a href="http://www.amazon.com/LINQ-Action-Fabrice-Marguerie/dp/1933988169/ref=pd_bbs_sr_2"&gt;LINQ en Action&lt;/a&gt; ...&amp;nbsp;y poco hay que&amp;nbsp;contar que no este en libros&amp;nbsp;ó en los&amp;nbsp;cientos de blogs que llevan escribiendo sobre LINQ desde hace mucho tiempo. Aún asi por lo menos iré escribiendo alguna cosilla sobre LINQ aunque solo sea para que no se me olvide como hacer ciertas cosas y tener que&amp;nbsp;volverlas a buscar&amp;nbsp;:P&lt;/p&gt; &lt;p&gt;Este es un ejemplo simple&amp;nbsp;de como lanzar una consulta Update-Select con LINQ sobre un DataTable, apoyandonos en el ya famoso &lt;a href="http://codebetter.com/blogs/glenn.block/archive/2008/08/19/foreach-a-simple-but-very-useful-extension-method.aspx"&gt;método extensor ForEach&lt;/a&gt; ... (que según me ha comentado un compañero es posible que aparezca en la BCL próximamente), lo que hace es en cada DataRow que cumple con las condiciones dadas introduce en la columna &amp;quot;Initial&amp;quot; la primera letra del nombre... (nada complicado vamos xD)&lt;/p&gt; &lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;EmployeesTable.AsEnumerable()&lt;/pre&gt;&lt;pre&gt;   .Where(EmployeeRow =&amp;gt; !EmployeeRow.IsNull(&lt;span class="str"&gt;&amp;quot;Country&amp;quot;&lt;/span&gt;) &amp;amp;&amp;amp; &lt;/pre&gt;&lt;pre class="alt"&gt;                  EmployeeRow.Field&amp;lt;String&amp;gt;(&lt;span class="str"&gt;&amp;quot;Country&amp;quot;&lt;/span&gt;) == &lt;span class="str"&gt;&amp;quot;UK&amp;quot;&lt;/span&gt; &amp;amp;&amp;amp;&lt;/pre&gt;&lt;pre&gt;                  !EmployeeRow.IsNull(&lt;span class="str"&gt;&amp;quot;FirstName&amp;quot;&lt;/span&gt;) &amp;amp;&amp;amp;&lt;/pre&gt;&lt;pre class="alt"&gt;                  EmployeeRow.Field&amp;lt;String&amp;gt;(&lt;span class="str"&gt;&amp;quot;FirstName&amp;quot;&lt;/span&gt;) != String.Empty)&lt;/pre&gt;&lt;pre&gt;   .ForEach(EmployeeRow =&amp;gt; EmployeeRow.SetField&amp;lt;String&amp;gt;(&lt;span class="str"&gt;&amp;quot;Initial&amp;quot;&lt;/span&gt;, &lt;/pre&gt;&lt;pre class="alt"&gt;                                EmployeeRow.Field&amp;lt;String&amp;gt;(&lt;span class="str"&gt;&amp;quot;FirstName&amp;quot;&lt;/span&gt;).Substring(0, 1)));&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;También empezaré ahora a escribir sobre WPF... que me toca ponerme las pilas :D&lt;/p&gt;
&lt;h5&gt;&lt;a href="http://vtortola.net/post/Update-Select-en-un-DataTable-con-LINQ.aspx"&gt;Update-Select en un DataTable con LINQ | vtortola.NET&lt;/a&gt;&lt;/h5&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=98435" width="1" height="1"&gt;</description><category domain="http://geeks.ms/blogs/vtortola/archive/tags/C_2300_+3.0/default.aspx">C# 3.0</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/.NET+3.5/default.aspx">.NET 3.5</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/LINQ/default.aspx">LINQ</category></item><item><title>Consumir un Webservice SSL</title><link>http://geeks.ms/blogs/vtortola/archive/2008/09/09/consumir-un-webservice-ssl.aspx</link><pubDate>Tue, 09 Sep 2008 17:33:18 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:98023</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>0</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=98023</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2008/09/09/consumir-un-webservice-ssl.aspx#comments</comments><description>&lt;p&gt;Mas sencillo de lo que imaginaba, se trata simplemente de definir el siguiente delegado &lt;a href="http://msdn.microsoft.com/en-us/library/system.net.servicepointmanager.servercertificatevalidationcallback.aspx"&gt;System.Net.ServicePointManager.ServerCertificateValidationCallback&lt;/a&gt;con la funcion que se encarga de validar el certificado.&lt;/p&gt; &lt;p&gt;Por ejemplo:&lt;/p&gt; &lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;System.Net.ServicePointManager.ServerCertificateValidationCallback =&lt;/pre&gt;&lt;pre&gt;    &lt;span class="kwrd"&gt;new&lt;/span&gt; System.Net.Security.RemoteCertificateValidationCallback(ValidateSSL);&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Y escribimos el metodo:&lt;/p&gt;
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="kwrd"&gt;static&lt;/span&gt; Boolean ValidateSSL(&lt;span class="kwrd"&gt;object&lt;/span&gt; sender, X509Certificate certificate, &lt;/pre&gt;&lt;pre&gt;                           X509Chain chain, SslPolicyErrors sslPolicyErrors)&lt;/pre&gt;&lt;pre class="alt"&gt;{&lt;/pre&gt;&lt;pre&gt;    &lt;span class="rem"&gt;// Validar el certificado...&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;    &lt;span class="rem"&gt;// Un ejemplo tosco para aceptar cualquiera sin errores.&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="kwrd"&gt;return&lt;/span&gt; sslPolicyErrors == SslPolicyErrors.None;&lt;/pre&gt;&lt;pre&gt;}&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;h5&gt;&lt;a href="http://www.vtortola.net/post/Consumir-un-Webservice-SSL.aspx"&gt;Consumir un Webservice SSL | vtortola.NET&lt;/a&gt;&lt;/h5&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=98023" width="1" height="1"&gt;</description><category domain="http://geeks.ms/blogs/vtortola/archive/tags/.NET+2.0/default.aspx">.NET 2.0</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/SSL/default.aspx">SSL</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/WebServices/default.aspx">WebServices</category></item><item><title>Cargar un tipo dinamicamente</title><link>http://geeks.ms/blogs/vtortola/archive/2008/07/17/cargar-un-tipo-dinamicamente.aspx</link><pubDate>Wed, 16 Jul 2008 22:30:10 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:91880</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>3</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=91880</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2008/07/17/cargar-un-tipo-dinamicamente.aspx#comments</comments><description>&lt;img style="border-top-width:0px;border-left-width:0px;border-bottom-width:0px;margin:0px 20px 0px 0px;border-right-width:0px;" alt="dynamictypeproject" src="http://geeks.ms/blogs/vtortola/WindowsLiveWriter/Cargaruntipodinamicamente_1468D/dynamictypeproject_3.png" align="left" border="0" /&gt;  &lt;p&gt;&amp;nbsp; Una aplicación modular suele ser una aplicación donde sus funcionalidades son opcionales, de forma que podemos quitar ó añadirlas según nos convenga.&amp;nbsp;La aplicación solo sabe que va a tratar con instancias que cumplen un&amp;nbsp;determinado contrato, ya sea&amp;nbsp;cumpliendo con&amp;nbsp;una &lt;a href="http://www.vtortola.net/post/El-uso-de-interfaces.aspx"&gt;interfaz&lt;/a&gt; ó&amp;nbsp;determinado tipo base (usando clases abstractas). Estos contratos suelen estar en ensamblados que conocen las dos partes, de forma que la aplicación espera una instancia de clase que cumple el contrato definido en el ensamblado común, y el ensamblado &amp;quot;opcional&amp;quot; provee una instancia de clase que cumple dicho contrato, dicho contrato ó acuerdo mutuo indica a la aplicación como usar dicha instancia. En el ejemplo de solución de Visual Studio que se ve&amp;nbsp;a la izquierda, &lt;strong&gt;LoadTypeTest&lt;/strong&gt; sería la aplicación, &lt;strong&gt;Common&lt;/strong&gt; el ensamblado compartido donde se definen los contratos y los tipos comunes,&amp;nbsp;y &lt;strong&gt;LibraryTest&lt;/strong&gt; donde se encuentra definida la clase, &lt;strong&gt;LoadTypeTest&lt;/strong&gt; y &lt;strong&gt;LibraryTest&lt;/strong&gt; tienen referenciado a &lt;strong&gt;Common&lt;/strong&gt;, pero se desconocen entre ellos.&lt;/p&gt; &lt;p&gt;En en ensamblado común he definido una &lt;a href="http://www.vtortola.net/post/El-uso-de-interfaces.aspx"&gt;interfaz&lt;/a&gt; y un delegado, que definen la forma en que la instancia &amp;quot;desconocida&amp;quot; se va a relacionar con la aplicación:&lt;/p&gt; &lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="kwrd"&gt;public&lt;/span&gt; &lt;span class="kwrd"&gt;delegate&lt;/span&gt; &lt;span class="kwrd"&gt;void&lt;/span&gt; DataArrival_(String Data);&lt;/pre&gt;&lt;pre&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="kwrd"&gt;public&lt;/span&gt; &lt;span class="kwrd"&gt;interface&lt;/span&gt; ITestInterface&lt;/pre&gt;&lt;pre&gt;{&lt;/pre&gt;&lt;pre class="alt"&gt;    String Name { get; }&lt;/pre&gt;&lt;pre&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="kwrd"&gt;event&lt;/span&gt; DataArrival_ DataArrival;&lt;/pre&gt;&lt;pre&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="kwrd"&gt;void&lt;/span&gt; SendData(String Data);&lt;/pre&gt;&lt;pre&gt;}&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Si la clase que que implementamos cumpliendo esta &lt;a href="http://www.vtortola.net/post/El-uso-de-interfaces.aspx"&gt;interfaz&lt;/a&gt;, tiene un constructor por defecto, tenemos dos formas de cargar el tipo dinámicamente:&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;&lt;a href="http://msdn.microsoft.com/es-es/library/cxz4wk15.aspx"&gt;Reflection&lt;/a&gt;:&lt;/strong&gt;&lt;/p&gt;
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;Assembly myAssembly = Assembly.LoadFrom(&lt;span class="str"&gt;&amp;quot;LibraryTest.dll&amp;quot;&lt;/span&gt;);&lt;/pre&gt;&lt;pre&gt;ITestInterface test2 = myAssembly.CreateInstance(&lt;span class="str"&gt;&amp;quot;LibraryTest.LibraryTest&amp;quot;&lt;/span&gt;) &lt;span class="kwrd"&gt;as&lt;/span&gt; ITestInterface;&lt;/pre&gt;&lt;pre class="alt"&gt;test2.DataArrival += &lt;span class="kwrd"&gt;new&lt;/span&gt; DataArrival_(&lt;span class="kwrd"&gt;delegate&lt;/span&gt;(String Data)&lt;/pre&gt;&lt;pre&gt;{&lt;/pre&gt;&lt;pre class="alt"&gt;    Console.WriteLine(&lt;span class="str"&gt;&amp;quot;Received: &amp;quot;&lt;/span&gt; + Data);&lt;/pre&gt;&lt;pre&gt;});&lt;/pre&gt;&lt;pre class="alt"&gt;test2.SendData(&lt;span class="str"&gt;&amp;quot;Hello &amp;quot;&lt;/span&gt; + test2.Name + &lt;span class="str"&gt;&amp;quot;!!&amp;quot;&lt;/span&gt;);&lt;/pre&gt;&lt;/div&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href="http://msdn.microsoft.com/es-es/library/system.reflection.assembly.aspx"&gt;Assembly&lt;/a&gt; 
&lt;li&gt;&lt;a href="http://msdn.microsoft.com/es-es/library/system.reflection.assembly.loadfrom.aspx"&gt;Assembly.LoadFrom()&lt;/a&gt; 
&lt;li&gt;&lt;a href="http://msdn.microsoft.com/es-es/library/system.reflection.assembly.createinstance.aspx"&gt;Assembly.CreateInstance()&lt;/a&gt;&lt;/li&gt;&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;&lt;a href="http://msdn.microsoft.com/es-es/library/72x4h507.aspx"&gt;Remoting&lt;/a&gt;:&lt;/strong&gt;&lt;/p&gt;
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;ObjectHandle obj = Activator.CreateInstance(&lt;span class="str"&gt;&amp;quot;LibraryTest&amp;quot;&lt;/span&gt;, &lt;span class="str"&gt;&amp;quot;LibraryTest.LibraryTest&amp;quot;&lt;/span&gt;);&lt;/pre&gt;&lt;pre&gt;ITestInterface test = obj.Unwrap() &lt;span class="kwrd"&gt;as&lt;/span&gt; ITestInterface;&lt;/pre&gt;&lt;pre class="alt"&gt;test.DataArrival += &lt;span class="kwrd"&gt;new&lt;/span&gt; DataArrival_(&lt;span class="kwrd"&gt;delegate&lt;/span&gt;(String Data)&lt;/pre&gt;&lt;pre&gt;    {&lt;/pre&gt;&lt;pre class="alt"&gt;        Console.WriteLine(&lt;span class="str"&gt;&amp;quot;Received: &amp;quot;&lt;/span&gt; + Data);&lt;/pre&gt;&lt;pre&gt;    });&lt;/pre&gt;&lt;pre class="alt"&gt;test.SendData(&lt;span class="str"&gt;&amp;quot;Hello &amp;quot;&lt;/span&gt;+ test.Name +&lt;span class="str"&gt;&amp;quot;!!&amp;quot;&lt;/span&gt;);&lt;/pre&gt;&lt;/div&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href="http://msdn.microsoft.com/es-es/library/system.runtime.remoting.objecthandle(VS.90).aspx"&gt;ObjectHandle&lt;/a&gt; 
&lt;li&gt;&lt;a href="http://msdn.microsoft.com/es-es/library/system.runtime.remoting.objecthandle.unwrap(VS.80).aspx"&gt;Activator.CreateInstance&lt;/a&gt; 
&lt;li&gt;&lt;a href="http://msdn.microsoft.com/es-es/library/system.runtime.remoting.objecthandle.unwrap(VS.80).aspx"&gt;ObjectHandle.Unwrap&lt;/a&gt;&lt;/li&gt;&lt;/ul&gt;
&lt;p&gt;En este contexto, nos valen ambos planteamientos por igual, ambos cargan la instancia en el mismo dominio de aplicación que la aplicación principal y su rendimiento es bastante similar, a excepción de la primera instancia que realiza Remoting, que parece que le cuesta un poco más:&lt;/p&gt;
&lt;p&gt;&lt;a href="http://geeks.ms/blogs/vtortola/WindowsLiveWriter/Cargaruntipodinamicamente_1468D/image.png"&gt;&lt;img style="border-top-width:0px;border-left-width:0px;border-bottom-width:0px;border-right-width:0px;" height="310" alt="image" src="http://geeks.ms/blogs/vtortola/WindowsLiveWriter/Cargaruntipodinamicamente_1468D/image_thumb.png" width="483" border="0" /&gt;&lt;/a&gt; &lt;/p&gt;
&lt;p&gt;Pero, cuando la instancia tiene un &lt;a href="http://www.vtortola.net/post/Constructores%2c-inicializacion-rapida-de-objetos-y-C-30.aspx"&gt;constructor&lt;/a&gt; parametrizado tendrémos que usar una mezcla de las&amp;nbsp;dos, ya que para poder invocar un constructor específico&amp;nbsp;debemos de proveer el tipo a &lt;em&gt;Activator.CreateInstance&lt;/em&gt;, que por supuesto lo podemos extraer con &lt;em&gt;Reflection&lt;/em&gt;; vamos a suponer que la calse &amp;quot;desconocida&amp;quot; espera dos parámetros, un &lt;em&gt;Int32&lt;/em&gt; y un &lt;em&gt;DataTable&lt;/em&gt; (ojo con el orden de los parámetros):&lt;/p&gt;
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;Assembly myAssembly = Assembly.LoadFrom(&lt;span class="str"&gt;&amp;quot;LibraryTest.dll&amp;quot;&lt;/span&gt;);&lt;/pre&gt;&lt;pre&gt;Type myType = myAssembly.GetType(&lt;span class="str"&gt;&amp;quot;LibraryTest.LibraryTest&amp;quot;&lt;/span&gt;);&lt;/pre&gt;&lt;pre class="alt"&gt;ITestInterface test = Activator.CreateInstance(myType,myIndex,myTable) &lt;span class="kwrd"&gt;as&lt;/span&gt; ITestInterface;&lt;/pre&gt;&lt;pre&gt;test.DataArrival += &lt;span class="kwrd"&gt;new&lt;/span&gt; DataArrival_(&lt;span class="kwrd"&gt;delegate&lt;/span&gt;(String Data)&lt;/pre&gt;&lt;pre class="alt"&gt;    {&lt;/pre&gt;&lt;pre&gt;        Console.WriteLine(&lt;span class="str"&gt;&amp;quot;Received: &amp;quot;&lt;/span&gt; + Data);&lt;/pre&gt;&lt;pre class="alt"&gt;    });&lt;/pre&gt;&lt;pre&gt;test.SendData(&lt;span class="str"&gt;&amp;quot;Hello &amp;quot;&lt;/span&gt; + test.Name + &lt;span class="str"&gt;&amp;quot;!!&amp;quot;&lt;/span&gt;);&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Pero... y si ni siquiera supiesemos que número de parámetros tiene el &lt;a href="http://www.vtortola.net/post/Constructores%2c-inicializacion-rapida-de-objetos-y-C-30.aspx"&gt;constructor&lt;/a&gt;... o que tipo de parámetros son... pues con &lt;em&gt;Reflection&lt;/em&gt; podemos interrogar al tipo para que nos de información sobre los constructores que hay en la clase y sus respectivos parámetros. Un ejemplo un poco tosco :&lt;/p&gt;
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;Assembly myAssembly = Assembly.LoadFrom(&lt;span class="str"&gt;&amp;quot;LibraryTest.dll&amp;quot;&lt;/span&gt;);&lt;/pre&gt;&lt;pre&gt;Type myType = myAssembly.GetType(&lt;span class="str"&gt;&amp;quot;LibraryTest.LibraryTest&amp;quot;&lt;/span&gt;);&lt;/pre&gt;&lt;pre class="alt"&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;&lt;span class="rem"&gt;// Interrogo al tipo para comprobar si existe el constructor&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;// que necesito.&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;Object[] constructorParameters = &lt;span class="kwrd"&gt;null&lt;/span&gt;;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="kwrd"&gt;foreach&lt;/span&gt; (ConstructorInfo constructor &lt;span class="kwrd"&gt;in&lt;/span&gt; myType.GetConstructors())&lt;/pre&gt;&lt;pre&gt;{&lt;/pre&gt;&lt;pre class="alt"&gt;    ParameterInfo[] parameters = constructor.GetParameters();&lt;/pre&gt;&lt;pre&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="kwrd"&gt;if&lt;/span&gt; ((parameters[0].ParameterType == &lt;span class="kwrd"&gt;typeof&lt;/span&gt;(Int32)) &amp;amp;&amp;amp;&lt;/pre&gt;&lt;pre&gt;        parameters[1].ParameterType == &lt;span class="kwrd"&gt;typeof&lt;/span&gt;(DataTable))&lt;/pre&gt;&lt;pre class="alt"&gt;    {&lt;/pre&gt;&lt;pre&gt;        constructorParameters = &lt;span class="kwrd"&gt;new&lt;/span&gt; Object[] {myIndex, myTable };&lt;/pre&gt;&lt;pre class="alt"&gt;    }&lt;/pre&gt;&lt;pre&gt;    parameters.ToString();&lt;/pre&gt;&lt;pre class="alt"&gt;}&lt;/pre&gt;&lt;pre&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;ITestInterface test = Activator.CreateInstance(myType,constructorParameters) &lt;span class="kwrd"&gt;as&lt;/span&gt; ITestInterface;&lt;/pre&gt;&lt;pre&gt;test.DataArrival += &lt;span class="kwrd"&gt;new&lt;/span&gt; DataArrival_(&lt;span class="kwrd"&gt;delegate&lt;/span&gt;(String Data)&lt;/pre&gt;&lt;pre class="alt"&gt;    {&lt;/pre&gt;&lt;pre&gt;        Console.WriteLine(&lt;span class="str"&gt;&amp;quot;Received: &amp;quot;&lt;/span&gt; + Data);&lt;/pre&gt;&lt;pre class="alt"&gt;    });&lt;/pre&gt;&lt;pre&gt;test.SendData(&lt;span class="str"&gt;&amp;quot;Hello &amp;quot;&lt;/span&gt; + test.Name + &lt;span class="str"&gt;&amp;quot;!!&amp;quot;&lt;/span&gt;);&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Como decía este es un ejemplo un poco tosco, podemos mejorar la lógica para detectar el constructor, ordenar los parámetros... etc.. etc..&lt;/p&gt;
&lt;p&gt;Lo máximo que sabe la aplicación sobre la clase, es su nombre y en que ensamblado esta, cosas que le podemos pasar&amp;nbsp;como parámetros&amp;nbsp;ó tenerlo alojado en un archivo de configuración, de forma que alterando dicho archivo la&amp;nbsp;aplicación usa una u otras funcionalidades.&amp;nbsp;Y con esto e imaginación puedes hacer tus arquitecturas tan inteligentes y escalables como tu quieras, de forma que sean capaces de cargar tipos sin conocerlos previamente y usarlos por medio de una interfaz ó clase abstracta. Si a esto le añades el uso de atributos como metadatos para describir las clases... aún puedes conseguir cosas más inteligentes y escalables,&amp;nbsp;a ver si tengo tiempo otro día para escribir sobre este tema, que es bastante apasionante :)&lt;/p&gt;
&lt;h5&gt;&lt;a href="http://www.vtortola.net/post/Cargar-un-tipo-dinamicamente.aspx"&gt;Cargar un tipo dinamicamente | vtortola.NET&lt;/a&gt;&lt;/h5&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=91880" width="1" height="1"&gt;</description><category domain="http://geeks.ms/blogs/vtortola/archive/tags/.NET+2.0/default.aspx">.NET 2.0</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/C_2300_+2.0/default.aspx">C# 2.0</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/Interfaces/default.aspx">Interfaces</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/Constructores/default.aspx">Constructores</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/Reflection/default.aspx">Reflection</category></item><item><title>Conversion de arrays sin cast directo con C#</title><link>http://geeks.ms/blogs/vtortola/archive/2008/07/12/conversion-de-arrays-sin-cast-directo-con-c.aspx</link><pubDate>Sat, 12 Jul 2008 17:03:15 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:91484</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>2</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=91484</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2008/07/12/conversion-de-arrays-sin-cast-directo-con-c.aspx#comments</comments><description>&lt;p&gt;Realizar casting entre clases es siempre sencillo, el inconveniente es cuando se trata de un arrays. Por ejemplo... sabiendo que la&amp;nbsp;clase &lt;em&gt;Manager&lt;/em&gt; deriva de &lt;em&gt;Employee&lt;/em&gt;, si tenemos un array de &lt;em&gt;Manager&lt;/em&gt;, es fácil convertirlo en un array de &lt;em&gt;Employee&lt;/em&gt; usando casting directo:&lt;/p&gt; &lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;Employee[] employees1 = (Employee[])managers;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Pero si tenemos un array de &lt;em&gt;Employee&lt;/em&gt; no es posible convertirlo en&amp;nbsp; un array de &lt;em&gt;Manager&lt;/em&gt; de la misma forma que tampoco podríamos hacer un casting directo&amp;nbsp;entre objetos simples. No se me&amp;nbsp;ocurre razón&amp;nbsp;cuerda para&amp;nbsp;querer hacer tal cosa, pero&amp;nbsp;otro ejemplo más cotidiano puede ser cuando intentamos mostrar el contenido de un array en una línea usando &lt;a href="http://msdn.microsoft.com/es-es/library/system.string.join.aspx"&gt;String.Join&lt;/a&gt;, nos daremos cuenta que&amp;nbsp;tiene que ser &lt;em&gt;String[]&lt;/em&gt;. Existen muchas situaciones donde no hay un casting directo.&lt;/p&gt;
&lt;p&gt;[more]&lt;/p&gt;
&lt;p&gt;Afortunadamente disponemos del método genérico&amp;nbsp;&lt;a href="http://msdn.microsoft.com/es-es/library/exc45z53(VS.90).aspx"&gt;Array.ConvertAll&amp;lt;,&amp;gt;&lt;/a&gt;&amp;nbsp;y del delegado genérico &lt;a href="http://msdn.microsoft.com/es-es/library/kt456a2y(VS.90).aspx"&gt;Converter&amp;lt;,&amp;gt;&lt;/a&gt; que nos pueden ayudar a simplificar estas cosas:&lt;/p&gt;
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;// Primero definimos como se convierte una clase en la otra&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;Converter&amp;lt;Employee, String&amp;gt; Employee2String = &lt;span class="kwrd"&gt;delegate&lt;/span&gt;(Employee m) { &lt;span class="kwrd"&gt;return&lt;/span&gt; m.Name; };&lt;/pre&gt;&lt;pre class="alt"&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;&lt;span class="rem"&gt;// Después convertimos todos los elementos del array usando ese delgado&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;String[] sArray = Array.ConvertAll&amp;lt;Employee,String&amp;gt;(Employees,Employee2String);&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Ó podemos hacerlo&amp;nbsp;en una sola línea aprovechando la inferencia de tipos:&lt;/p&gt;
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;String[] sArray = Array.ConvertAll&amp;lt;Employee,String&amp;gt;(Employees,&lt;span class="kwrd"&gt;delegate&lt;/span&gt;(Employee m) { &lt;span class="kwrd"&gt;return&lt;/span&gt; m.Name; });&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;h5&gt;&lt;a href="http://www.vtortola.net/post/Conversion-de-arrays-sin-cast-directo-con-C.aspx"&gt;Conversion de arrays sin cast directo con C# | vtortola.NET&lt;/a&gt;&lt;/h5&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=91484" width="1" height="1"&gt;</description><category domain="http://geeks.ms/blogs/vtortola/archive/tags/.NET+2.0/default.aspx">.NET 2.0</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/C_2300_+2.0/default.aspx">C# 2.0</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/Gen_26002300_233_3B00_ricos/default.aspx">Gen&amp;#233;ricos</category></item><item><title>Desechable o no desechable</title><link>http://geeks.ms/blogs/vtortola/archive/2008/07/11/desechable-o-no-desechable.aspx</link><pubDate>Fri, 11 Jul 2008 21:45:38 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:91454</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>2</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=91454</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2008/07/11/desechable-o-no-desechable.aspx#comments</comments><description>&lt;p&gt;La interfaz &lt;a href="http://www.vtortola.net/post/Objetos-desechables-con-la-interfaz-IDisposable.aspx"&gt;IDisposable&lt;/a&gt; nos provee del método .Dispose() que utilizamos para liberar los recursos que esta usando ese objeto, pero dicho método... no deja de ser un simple método ;) Solo hace falta hacer una pequeña prueba para darse cuenta:&lt;/p&gt; &lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   1:  &lt;/span&gt;&lt;span class="kwrd"&gt;class&lt;/span&gt; Program&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;   2:  &lt;/span&gt;{&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   3:  &lt;/span&gt;    &lt;span class="kwrd"&gt;static&lt;/span&gt; &lt;span class="kwrd"&gt;void&lt;/span&gt; Main(&lt;span class="kwrd"&gt;string&lt;/span&gt;[] args)&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;   4:  &lt;/span&gt;    {&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   5:  &lt;/span&gt;        Desechable test = &lt;span class="kwrd"&gt;new&lt;/span&gt; Desechable();&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;   6:  &lt;/span&gt;          &lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   7:  &lt;/span&gt;        test.Dispose();&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;   8:  &lt;/span&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   9:  &lt;/span&gt;        Console.WriteLine(test.Cadena??&lt;span class="str"&gt;&amp;quot;Muerto&amp;quot;&lt;/span&gt;); &lt;span class="rem"&gt;// Muestra: Vivo!&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  10:  &lt;/span&gt;        Console.ReadKey(&lt;span class="kwrd"&gt;true&lt;/span&gt;);&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  11:  &lt;/span&gt;    }&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  12:  &lt;/span&gt;}&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  13:  &lt;/span&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  14:  &lt;/span&gt;&lt;span class="kwrd"&gt;class&lt;/span&gt; Desechable : IDisposable&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  15:  &lt;/span&gt;{&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  16:  &lt;/span&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; String Cadena = &lt;span class="str"&gt;&amp;quot;Vivo!&amp;quot;&lt;/span&gt;;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  17:  &lt;/span&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  18:  &lt;/span&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; &lt;span class="kwrd"&gt;void&lt;/span&gt; Dispose()&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  19:  &lt;/span&gt;    {&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  20:  &lt;/span&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  21:  &lt;/span&gt;    }&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  22:  &lt;/span&gt;}&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Ok ok... un poco más complejo:&lt;/p&gt;
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   1:  &lt;/span&gt;&lt;span class="kwrd"&gt;class&lt;/span&gt; Program&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;   2:  &lt;/span&gt;{&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   3:  &lt;/span&gt;    &lt;span class="kwrd"&gt;static&lt;/span&gt; &lt;span class="kwrd"&gt;void&lt;/span&gt; Main(&lt;span class="kwrd"&gt;string&lt;/span&gt;[] args)&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;   4:  &lt;/span&gt;    {&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   5:  &lt;/span&gt;        Desechable test = &lt;span class="kwrd"&gt;new&lt;/span&gt; Desechable();&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;   6:  &lt;/span&gt;        WeakReference wr = &lt;span class="kwrd"&gt;new&lt;/span&gt; WeakReference(test.Tabla.Columns[0]);&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   7:  &lt;/span&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;   8:  &lt;/span&gt;        test.Dispose();&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   9:  &lt;/span&gt;        test = &lt;span class="kwrd"&gt;null&lt;/span&gt;;&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  10:  &lt;/span&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  11:  &lt;/span&gt;        Console.WriteLine(((DataColumn)wr.Target).ColumnName); &lt;span class="rem"&gt;// Muestra &amp;quot;Columna&amp;quot;&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  12:  &lt;/span&gt;        Console.ReadKey(&lt;span class="kwrd"&gt;true&lt;/span&gt;);&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  13:  &lt;/span&gt;    }&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  14:  &lt;/span&gt;}&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  15:  &lt;/span&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  16:  &lt;/span&gt;&lt;span class="kwrd"&gt;class&lt;/span&gt; Desechable : IDisposable&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  17:  &lt;/span&gt;{&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  18:  &lt;/span&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; DataTable Tabla = &lt;span class="kwrd"&gt;new&lt;/span&gt; DataTable();&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  19:  &lt;/span&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  20:  &lt;/span&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; Desechable()&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  21:  &lt;/span&gt;    {&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  22:  &lt;/span&gt;        Tabla.Columns.Add(&lt;span class="kwrd"&gt;new&lt;/span&gt; DataColumn(&lt;span class="str"&gt;&amp;quot;Columna&amp;quot;&lt;/span&gt;));&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  23:  &lt;/span&gt;    }&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  24:  &lt;/span&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  25:  &lt;/span&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; &lt;span class="kwrd"&gt;void&lt;/span&gt; Dispose()&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  26:  &lt;/span&gt;    {&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  27:  &lt;/span&gt;        Tabla.Dispose();&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  28:  &lt;/span&gt;    }&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  29:  &lt;/span&gt;}&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;El resultado cambia si en la línea 10 hacemos un &lt;a href="http://msdn.microsoft.com/es-es/library/system.gc.collect.aspx"&gt;GC.Collect()&lt;/a&gt; ;D&lt;/p&gt;
&lt;p&gt;Como vemos, el único que puede liberar memoria en el .NET Framework es el &lt;a href="http://msdn.microsoft.com/es-es/library/0xy59wtx(vs.80).aspx"&gt;Garbage Collector&lt;/a&gt;, por lo que el método .Dispose() no libera memoria in libera nada, solo nos sirve para asegurar que el objeto que estamos desechando ha cerrado correctamente todos sus recursos y podemos olvidarnos de él, ya se encargará el GC de liberar la memoria cuando lo crea necesario.&lt;/p&gt;
&lt;p&gt;Entonces, implementar la interfaz IDisposable no hace nuestros objetos &amp;quot;destruibles&amp;quot; bajo demanda, ni setear todos los campos a null en Dispose no va a hacer que sea recolectado más deprisa, ni no hacerlo va a evitar que sea recolectado, ni debemos des-subscribir los eventos...&lt;/p&gt;
&lt;p&gt;Por lo tanto, debemos implementar &lt;a href="http://www.vtortola.net/post/Objetos-desechables-con-la-interfaz-IDisposable.aspx"&gt;el patrón IDisposable&lt;/a&gt; en una clase siempre que:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Nuestra clase deriva de una clase que lo implementa. 
&lt;li&gt;Nuestra clase esta compuesta de otras clases que lo implementan. 
&lt;li&gt;Hagamos uso de recursos no administrados.&lt;/li&gt;&lt;/ul&gt;
&lt;p&gt;Para todo lo demás... &lt;strike&gt;mastercard&lt;/strike&gt; confia en el GC :D&lt;/p&gt;
&lt;p&gt;Un&amp;nbsp;tema que causa controversia en este aspecto es... ¿que pasa con los delegados? ¿Como el estar subscrito a delegados afecta a la recolección de memoria? Bien, el estar subscrito a un delegado de una clase, no afecta en su recolección:&lt;/p&gt;
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   1:  &lt;/span&gt;&lt;span class="kwrd"&gt;class&lt;/span&gt; Program&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;   2:  &lt;/span&gt;{&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   3:  &lt;/span&gt;    &lt;span class="kwrd"&gt;static&lt;/span&gt; &lt;span class="kwrd"&gt;void&lt;/span&gt; Main(&lt;span class="kwrd"&gt;string&lt;/span&gt;[] args)&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;   4:  &lt;/span&gt;    {&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   5:  &lt;/span&gt;        MiClase test = &lt;span class="kwrd"&gt;new&lt;/span&gt; MiClase();&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;   6:  &lt;/span&gt;        WeakReference wr = &lt;span class="kwrd"&gt;new&lt;/span&gt; WeakReference(test);&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   7:  &lt;/span&gt;        &lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;   8:  &lt;/span&gt;        test.MiEvento += &lt;span class="kwrd"&gt;new&lt;/span&gt; EventHandler(test_MiEvento);&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   9:  &lt;/span&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  10:  &lt;/span&gt;        test = &lt;span class="kwrd"&gt;null&lt;/span&gt;;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  11:  &lt;/span&gt;        GC.Collect();&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  12:  &lt;/span&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  13:  &lt;/span&gt;        Console.WriteLine(wr.IsAlive ? &lt;span class="str"&gt;&amp;quot;Vivo&amp;quot;&lt;/span&gt; : &lt;span class="str"&gt;&amp;quot;Muerto&amp;quot;&lt;/span&gt;); &lt;span class="rem"&gt;// Muestra &amp;quot;Muerto&amp;quot;&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  14:  &lt;/span&gt;        Console.ReadKey(&lt;span class="kwrd"&gt;true&lt;/span&gt;);&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  15:  &lt;/span&gt;    }&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  16:  &lt;/span&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  17:  &lt;/span&gt;    &lt;span class="kwrd"&gt;static&lt;/span&gt; &lt;span class="kwrd"&gt;void&lt;/span&gt; test_MiEvento(&lt;span class="kwrd"&gt;object&lt;/span&gt; sender, EventArgs e)&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  18:  &lt;/span&gt;    {&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  19:  &lt;/span&gt;        &lt;span class="kwrd"&gt;throw&lt;/span&gt; &lt;span class="kwrd"&gt;new&lt;/span&gt; NotImplementedException();&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  20:  &lt;/span&gt;    }&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  21:  &lt;/span&gt;}&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  22:  &lt;/span&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  23:  &lt;/span&gt;&lt;span class="kwrd"&gt;class&lt;/span&gt; MiClase&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  24:  &lt;/span&gt;{&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  25:  &lt;/span&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; &lt;span class="kwrd"&gt;event&lt;/span&gt; EventHandler MiEvento;&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  26:  &lt;/span&gt;}&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Pero al revés, es decir, que una clase este subscrita a uno de nuestros delegados... si provoca que el objeto no pueda ser recolectado:&lt;/p&gt;
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   1:  &lt;/span&gt;&lt;span class="kwrd"&gt;class&lt;/span&gt; Program&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;   2:  &lt;/span&gt;{&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   3:  &lt;/span&gt;    &lt;span class="kwrd"&gt;static&lt;/span&gt; &lt;span class="kwrd"&gt;event&lt;/span&gt; EventHandler Evento;&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;   4:  &lt;/span&gt;    &lt;span class="kwrd"&gt;static&lt;/span&gt; &lt;span class="kwrd"&gt;void&lt;/span&gt; Main(&lt;span class="kwrd"&gt;string&lt;/span&gt;[] args)&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   5:  &lt;/span&gt;    {&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;   6:  &lt;/span&gt;        MiClase test = &lt;span class="kwrd"&gt;new&lt;/span&gt; MiClase();&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   7:  &lt;/span&gt;        WeakReference wr = &lt;span class="kwrd"&gt;new&lt;/span&gt; WeakReference(test);&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;   8:  &lt;/span&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;   9:  &lt;/span&gt;        Evento += test.Manejador_Evento;&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  10:  &lt;/span&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  11:  &lt;/span&gt;        test = &lt;span class="kwrd"&gt;null&lt;/span&gt;;&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  12:  &lt;/span&gt;        GC.Collect();&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  13:  &lt;/span&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  14:  &lt;/span&gt;        Console.WriteLine(wr.IsAlive ? &lt;span class="str"&gt;&amp;quot;Vivo&amp;quot;&lt;/span&gt; : &lt;span class="str"&gt;&amp;quot;Muerto&amp;quot;&lt;/span&gt;); &lt;span class="rem"&gt;// Muestra &amp;quot;Vivo&amp;quot;&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  15:  &lt;/span&gt;        Console.WriteLine(Evento.GetInvocationList().Length); &lt;span class="rem"&gt;// Muestra 1&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  16:  &lt;/span&gt;        Console.ReadKey(&lt;span class="kwrd"&gt;true&lt;/span&gt;);&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  17:  &lt;/span&gt;    }&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  18:  &lt;/span&gt;}&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  19:  &lt;/span&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  20:  &lt;/span&gt;&lt;span class="kwrd"&gt;class&lt;/span&gt; MiClase&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  21:  &lt;/span&gt;{&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  22:  &lt;/span&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; &lt;span class="kwrd"&gt;void&lt;/span&gt; Manejador_Evento(&lt;span class="kwrd"&gt;object&lt;/span&gt; sender, EventArgs e)&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  23:  &lt;/span&gt;    {&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  24:  &lt;/span&gt;        &lt;span class="kwrd"&gt;throw&lt;/span&gt; &lt;span class="kwrd"&gt;new&lt;/span&gt; NotImplementedException();&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="lnum"&gt;  25:  &lt;/span&gt;    }&lt;/pre&gt;&lt;pre&gt;&lt;span class="lnum"&gt;  26:  &lt;/span&gt;}&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Y ojo, que los delegados son muy comodos para ejecutar muchos métodos de una pasada (por ejemplo podríamos tener una serie de objetos subscritos a un delegado y cada vez que invocaramos a este se ejecutaria ese método en todos los objetos), pero como veis pueden causar un memory leak; aunque en ese caso poco podemos hacer desde el método Dispose ya que es otra clase la que ha de desuscribirse.&lt;/p&gt;
&lt;p&gt;Saludos desde el frio Dublin donde el Verano es una broma de mal gusto.&lt;/p&gt;
&lt;h5&gt;&lt;a href="http://www.vtortola.net/post/Desechable-o-no-desechable.aspx"&gt;Desechable o no desechable| vtortola.NET&lt;/a&gt;&lt;/h5&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=91454" width="1" height="1"&gt;</description><category domain="http://geeks.ms/blogs/vtortola/archive/tags/Memoria/default.aspx">Memoria</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/.NET+2.0/default.aspx">.NET 2.0</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/C_2300_+2.0/default.aspx">C# 2.0</category></item><item><title>Constructores, inicializacion rapida de objetos y C# 3.0</title><link>http://geeks.ms/blogs/vtortola/archive/2008/07/10/constructores-inicializacion-rapida-de-objetos-y-c-3-0.aspx</link><pubDate>Thu, 10 Jul 2008 20:55:13 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:91270</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>3</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=91270</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2008/07/10/constructores-inicializacion-rapida-de-objetos-y-c-3-0.aspx#comments</comments><description>&lt;p&gt;La &lt;a href="http://www.variablenotfound.com/2008/03/inicializacin-rpida-de-objetos-en-c-30.html"&gt;inicialización rápida de objetos&lt;/a&gt; es una nueva e interesante&amp;nbsp;característica de C# 3.0, pero me gustaria reflexionar un poco sobre su uso y el de nuestros amigos los constructores.&lt;/p&gt; &lt;p&gt;Un &lt;a href="http://msdn.microsoft.com/es-es/library/ace5hbzh.aspx"&gt;constructor&lt;/a&gt; es el método de una instancia que implementa las acciones necesarias para inicializar la instancia de la clase, y es invocado por el operador &lt;a href="http://msdn.microsoft.com/es-es/library/51y09td4.aspx"&gt;new&lt;/a&gt; cuando instanciamos dicha clase.&amp;nbsp; Por lo tanto, cuando desarrollamos una clase, el ó los constructores deben de tener la capacidad de inicializar los aspectos básicos de funcionamiento del objeto.&lt;/p&gt; &lt;p&gt;En C#, cuando no implementamos&amp;nbsp;ningún constructor, el compilador asume que tenemos un constructor sin parámetros, es decir, esto:&lt;/p&gt; &lt;p&gt;[more]&lt;/p&gt; &lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="kwrd"&gt;class&lt;/span&gt; MyClass&lt;/pre&gt;&lt;pre&gt;{&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; String Field1 { get; &lt;span class="kwrd"&gt;private&lt;/span&gt; set; }&lt;/pre&gt;&lt;pre&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; String Field2 { get; &lt;span class="kwrd"&gt;private&lt;/span&gt; set; }&lt;/pre&gt;&lt;pre class="alt"&gt;}&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;es lo mismo que esto:&lt;/p&gt;
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="kwrd"&gt;class&lt;/span&gt; MyClass&lt;/pre&gt;&lt;pre&gt;{&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; String Field1 { get; &lt;span class="kwrd"&gt;private&lt;/span&gt; set; }&lt;/pre&gt;&lt;pre&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; String Field2 { get; &lt;span class="kwrd"&gt;private&lt;/span&gt; set; }&lt;/pre&gt;&lt;pre class="alt"&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; MyClass()&lt;/pre&gt;&lt;pre class="alt"&gt;    {&lt;/pre&gt;&lt;pre&gt;    }&lt;/pre&gt;&lt;pre class="alt"&gt;}&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;En el momento que definamos un constructor con parámetros, el compilador deja de asumir la existencia del constructor sin ellos, el motivo me parece más que obvio, &lt;strong&gt;si definimos un constructor con parámetros estamos diciendo que nuestra clase necesita &amp;quot;otras cosas&amp;quot; para poder inicializarse correctamente&lt;/strong&gt;; si queremos tener otro sin parámetros tendremos que definirlo explicitamente. &lt;/p&gt;
&lt;p&gt;Una ve las ventajas de usar un constructor paramétrizado, es por&amp;nbsp;ejemplo inicializar&amp;nbsp;propiedades públicas con setter privado, y modificarlas desde el constructor en base a los parámetros (seguro que no lo has hecho nunca xD); pero la principal ventaja es que le dice al programador que se necesita para ser inicializado y poder empezar a trabajar. A veces no necesitamos parámetros y otras veces&amp;nbsp;es inevitable y debemos definir un constructor sin parámetros, como por ejemplo para permitir la &lt;a href="http://msdn.microsoft.com/es-es/library/182eeyhh.aspx"&gt;serialización en Xml&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;Definir constructores es bastante llevadero y poco pesado, ya que gracias a la &lt;strong&gt;sobrecarga&lt;/strong&gt;, se escriben rápido, sin repetir el código en cada uno de ellos y queda bastante claro:&lt;/p&gt;
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="kwrd"&gt;class&lt;/span&gt; MyControl : Control&lt;/pre&gt;&lt;pre&gt;{&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; String Field1 { get; &lt;span class="kwrd"&gt;private&lt;/span&gt; set; }&lt;/pre&gt;&lt;pre&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; String Field2 { get; &lt;span class="kwrd"&gt;private&lt;/span&gt; set; }&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; String Field3 { get; &lt;span class="kwrd"&gt;private&lt;/span&gt; set; }&lt;/pre&gt;&lt;pre&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="rem"&gt;// base: nos permite pasar parámetros a la &lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;    &lt;span class="rem"&gt;// clase de la que heredamos&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; MyControl(Control parent, String text, String field1)&lt;/pre&gt;&lt;pre&gt;        : &lt;span class="kwrd"&gt;base&lt;/span&gt;(parent, text)&lt;/pre&gt;&lt;pre class="alt"&gt;    {&lt;/pre&gt;&lt;pre&gt;        &lt;span class="kwrd"&gt;this&lt;/span&gt;.Field1 = field1;&lt;/pre&gt;&lt;pre class="alt"&gt;    }&lt;/pre&gt;&lt;pre&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="rem"&gt;// this: nos permite invocar a otro constructor&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;    &lt;span class="rem"&gt;// de la misma clase, de forma que lo que escribimos&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="rem"&gt;// en este prosigue la labor del otro, evitandonos escribir&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;    &lt;span class="rem"&gt;// otra vez lo mismo para cada constructor.&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; MyControl(Control parent, String text, String field1, String field2)&lt;/pre&gt;&lt;pre&gt;        : &lt;span class="kwrd"&gt;this&lt;/span&gt;(parent, text, field1)&lt;/pre&gt;&lt;pre class="alt"&gt;    {&lt;/pre&gt;&lt;pre&gt;        &lt;span class="kwrd"&gt;this&lt;/span&gt;.Field2 = field2;&lt;/pre&gt;&lt;pre class="alt"&gt;    }&lt;/pre&gt;&lt;pre&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="rem"&gt;// this: nos permite llamar a cualquier constructor&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;    &lt;span class="rem"&gt;// de la misma clase.&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; MyControl(Control parent, String text, String field1, String field2, String field3)&lt;/pre&gt;&lt;pre&gt;        : &lt;span class="kwrd"&gt;this&lt;/span&gt;(parent, text, field1,field2)&lt;/pre&gt;&lt;pre class="alt"&gt;    {&lt;/pre&gt;&lt;pre&gt;        &lt;span class="kwrd"&gt;this&lt;/span&gt;.Field3 = field3;&lt;/pre&gt;&lt;pre class="alt"&gt;    }&lt;/pre&gt;&lt;pre&gt;}&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;También se pueden&amp;nbsp;definir &lt;a href="http://msdn.microsoft.com/es-es/library/ms173121.aspx"&gt;modificadores de acceso&lt;/a&gt; en los constructores, de forma que haya constructores que solo se puedan usar desde&amp;nbsp;dentro de la misma clase(private),&amp;nbsp;clase derivada(protected), ensamblado(internal) ó por todo el mundo(public). Útil para controlar desde donde se pueden instanciar nuestros objetos, ó cuantas veces, como en el patrón &lt;a href="http://www.yoda.arachsys.com/csharp/singleton.html"&gt;Singleton&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;Además,&amp;nbsp;podemos definir un &lt;a href="http://msdn.microsoft.com/es-es/library/k9x6w0hc(VS.80).aspx"&gt;constructor estático&lt;/a&gt;, sin parámetros, sin modificadores de acceso,&amp;nbsp;imposible de invocar directamente... pero que nos permite inicializar lo que queramos antes que nigún miembro de la clase, estático ó de instancia, sea usado.&lt;/p&gt;
&lt;p&gt;Bien, en C# 3.0 la inicialización rápida&amp;nbsp;de objetos, permiten inicializar las propiedades públicas de una clase de una pasada:&lt;/p&gt;
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="kwrd"&gt;class&lt;/span&gt; MyControl : Control&lt;/pre&gt;&lt;pre&gt;{&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; String Field1 { get;  set; }&lt;/pre&gt;&lt;pre&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; String Field2 { get;  set; }&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; String Field3 { get;  set; }&lt;/pre&gt;&lt;pre&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; String Field4 { get; &lt;span class="kwrd"&gt;private&lt;/span&gt; set; }&lt;/pre&gt;&lt;pre class="alt"&gt;}&lt;/pre&gt;&lt;pre&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="kwrd"&gt;static&lt;/span&gt; &lt;span class="kwrd"&gt;void&lt;/span&gt; Main()&lt;/pre&gt;&lt;pre&gt;{&lt;/pre&gt;&lt;pre class="alt"&gt;    MyControl mc = &lt;span class="kwrd"&gt;new&lt;/span&gt; MyControl() { Field1 = &lt;span class="str"&gt;&amp;quot;f1&amp;quot;&lt;/span&gt;, Field2 = &lt;span class="str"&gt;&amp;quot;f2&amp;quot;&lt;/span&gt;, Field3 = &lt;span class="str"&gt;&amp;quot;f3&amp;quot;&lt;/span&gt; };&lt;/pre&gt;&lt;pre&gt;}&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;No voy a discutir de lo útil que es, porque definitivamente lo es, pero por supuesto no es una caracteristica para reemplazar los constructores porque:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;No podemos inicializar campos privados ó propiedades públicas con &lt;em&gt;setter&lt;/em&gt; privado. 
&lt;li&gt;Puede que necesitamos ejecutar alguna lógica ó incluso otros métodos&amp;nbsp;en función del tipo de parámetros. 
&lt;li&gt;No denota cuales son las propiedades que necesita tener configuradas para poder considerarse totalmente inicializado, de cara a alguien que consuma nuestra clase a posteriori. Esto me parece lo más importante, ya que el código debe intentar ser autodescriptivo.&lt;/li&gt;&lt;/ul&gt;
&lt;p&gt;Al igual que los métodos parciales, métodos extensores ó tipos anónimos, es una nueva caracteristica para tener en cuenta y para usar cuando sea apropiado, no viene a reemplazar nada, viene a complementar para &amp;quot;esos casos&amp;quot; donde hace falta.&lt;/p&gt;
&lt;p&gt;Si tu clase necesita datos ó ser inicializada, implementa un constructor parametrizado. Por la salud mental de nuestros compañeros de trabajo, hagamos un buen uso del lenguaje :D&lt;/p&gt;
&lt;h5&gt;&lt;a href="http://www.vtortola.net/post/Constructores%2c-inicializacion-rapida-de-objetos-y-C-30.aspx"&gt;Constructores, inicializacion rapida de objetos y C# 3.0 | vtortola.NET&lt;/a&gt;&lt;/h5&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=91270" width="1" height="1"&gt;</description><category domain="http://geeks.ms/blogs/vtortola/archive/tags/C_2300_+3.0/default.aspx">C# 3.0</category></item><item><title>Asi da gusto usar Windows Vista</title><link>http://geeks.ms/blogs/vtortola/archive/2008/07/09/asi-da-gusto-usar-windows-vista.aspx</link><pubDate>Wed, 09 Jul 2008 21:15:22 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:91191</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>11</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=91191</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2008/07/09/asi-da-gusto-usar-windows-vista.aspx#comments</comments><description>&lt;p&gt;Pedazo de maquinón que estrené en el trabajo&amp;nbsp;y con el que estoy más que contento, es un placer trabajar así.&lt;/p&gt; &lt;p&gt;&lt;img style="border-top-width:0px;border-left-width:0px;border-bottom-width:0px;border-right-width:0px;" height="180" alt="image" src="http://geeks.ms/blogs/vtortola/WindowsLiveWriter/AsidagustousarWindowsVista_13632/image_3.png" width="516" border="0" /&gt; &lt;/p&gt; &lt;p&gt;Mi jefe es de esas personas que sabe como hacerte feliz. Después de algo más de una&amp;nbsp;semana trabajando con él, cuando cojo&amp;nbsp;mi portátil ya no es lo mismo...&amp;nbsp;definitivamente tengo que hacerme con uno de estos para mi casa :D&lt;/p&gt; &lt;p&gt;El monitor no es que se quede atrás:&lt;/p&gt; &lt;p&gt;&lt;img style="border-top-width:0px;border-left-width:0px;border-bottom-width:0px;border-right-width:0px;" height="494" alt="image" src="http://geeks.ms/blogs/vtortola/WindowsLiveWriter/AsidagustousarWindowsVista_13632/image_2.png" width="600" border="0" /&gt; &lt;/p&gt; &lt;h6&gt;&lt;/h6&gt; &lt;h6&gt;&lt;a href="http://www.vtortola.net/post/Asi-da-gusto-usar-Windows-Vista.aspx"&gt;Asi da gusto usar Windows Vista| vtortola.NET&lt;/a&gt;&lt;/h6&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=91191" width="1" height="1"&gt;</description><category domain="http://geeks.ms/blogs/vtortola/archive/tags/Vista/default.aspx">Vista</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/Personal/default.aspx">Personal</category></item><item><title>Asistente P/Invoke Interop</title><link>http://geeks.ms/blogs/vtortola/archive/2008/07/08/asistente-p-invoke-interop.aspx</link><pubDate>Mon, 07 Jul 2008 22:37:37 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:91032</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>3</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=91032</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2008/07/08/asistente-p-invoke-interop.aspx#comments</comments><description>&lt;p&gt;Si trabajas con p/invoke tanto habitual como eventualmente y &lt;a href="http://pinvoke.net/"&gt;pinvoke.net&lt;/a&gt; esta en tus bookmarks... esta herramienta no te va a dejar indiferente :D Leo en el &lt;a href="http://blogs.msdn.com/bclteam/"&gt;blog del BCL Team&lt;/a&gt;:&lt;/p&gt; &lt;p&gt;&lt;em&gt;El equipo Interop ha publicado recientemente una nueva herramienta llamada &lt;/em&gt;&lt;a href="http://www.codeplex.com/clrinterop/Release/ProjectReleases.aspx?ReleaseId=14120"&gt;&lt;em&gt;P/Invoke Interop Assistant&lt;/em&gt;&lt;/a&gt;&lt;em&gt;. Esta herramienta genera automáticamente las declaraciones en C# ó VB.NET de las llamadas p/invoke nativas. Incluye una búsqueda rápida por las librerias comunes&amp;nbsp;Win32 y permite&amp;nbsp;generar las declaraciones para cualquier otra libreria nativa simplemente pasando la firma nativa. Esto hace mucho más facil trabajar con interop correctamente, sin tener que comprender todas las reglas y atributos usados cuando&amp;nbsp;&amp;quot;conecta&amp;quot; el desarrollo administrado y no administrado.&amp;nbsp;`&lt;/em&gt;&lt;/p&gt; &lt;p&gt;&lt;a href="http://geeks.ms/blogs/vtortola/WindowsLiveWriter/AsistentePInvokeInterop_14B1E/image.png"&gt;&lt;img style="border-top-width:0px;border-left-width:0px;border-bottom-width:0px;border-right-width:0px;" height="483" alt="image" src="http://geeks.ms/blogs/vtortola/WindowsLiveWriter/AsistentePInvokeInterop_14B1E/image_thumb.png" width="648" border="0" /&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;&lt;em&gt;La herramienta fue publicada&amp;nbsp;en&amp;nbsp;&lt;/em&gt;&lt;a href="http://msdn.microsoft.com/en-us/magazine/default.aspx"&gt;&lt;em&gt;MSDN Magazine&lt;/em&gt;&lt;/a&gt;&amp;nbsp;&lt;em&gt;como parte del artículo &lt;/em&gt;&lt;a href="http://msdn.microsoft.com/en-us/magazine/cc164193.aspx"&gt;&lt;em&gt;Marshaling between Managed and Unmanaged Code&lt;/em&gt;&lt;/a&gt;&amp;nbsp;&lt;em&gt;en Enero. Ahora esta en &lt;/em&gt;&lt;a href="http://www.codeplex.com/clrinterop/Release/ProjectReleases.aspx?ReleaseId=14120"&gt;&lt;em&gt;CodePlex&lt;/em&gt;&lt;/a&gt;&lt;em&gt;&amp;nbsp;junto al código fuente. Altamente recomendado echarle un ojo!!&lt;/em&gt;&lt;/p&gt; &lt;p&gt;Impresionante!! La estoy usando y me va a ahorrar mucho tiempo en búsquedas :D Obviamente, no va a substituir a &lt;a href="http://pinvoke.net/"&gt;pinvoke.net&lt;/a&gt; porque dicha web tiene algo muy importante, ejemplos y tips (que habría sido de mi sin esta web estas dos semanas...), mientras que este programa solo te proporciona las firmas... pero esta claro que es una herramienta indispensable si se trabaja con interop :)&lt;/p&gt; &lt;h6&gt;&lt;a href="http://www.vtortola.net/post/Asistente-PInvoke-Interop.aspx"&gt;Asistente P/Invoke Interop | vtortola.NET&lt;/a&gt;&lt;/h6&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=91032" width="1" height="1"&gt;</description><category domain="http://geeks.ms/blogs/vtortola/archive/tags/.NET+2.0/default.aspx">.NET 2.0</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/C_2300_+2.0/default.aspx">C# 2.0</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/Interop/default.aspx">Interop</category></item><item><title>Recursividad y yield return. Haciendo queries a colecciones en arbol en C# 2.0</title><link>http://geeks.ms/blogs/vtortola/archive/2008/07/05/recursividad-y-yield-return-haciendo-queries-a-colecciones-en-arbol-en-c-2-0.aspx</link><pubDate>Sat, 05 Jul 2008 16:53:57 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:90794</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>1</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=90794</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2008/07/05/recursividad-y-yield-return-haciendo-queries-a-colecciones-en-arbol-en-c-2-0.aspx#comments</comments><description>&lt;p&gt;Estoy disfrutando de lo que será mi último proyecto en&amp;nbsp;C# 2.0 y&amp;nbsp;.NET 2.0 antes de pasar a WPF,&amp;nbsp;y la verdad es que se hace amargo algunas veces cuando ya conoces C# 3.0, por ejemplo se hecha de menos LINQ :D&lt;/p&gt; &lt;p&gt;En este artículo quiero demostrar como hacer queries a una colección de elementos en forma de arbol desde C# 2.0, de forma que se pueda definir el tipo de colección,&amp;nbsp;criterio de búsqueda que se quiere usar y obtener los resultado conforme se vayan obteniendo.&lt;/p&gt; &lt;p&gt;Una &lt;a href="http://es.wikipedia.org/wiki/Funci%C3%B3n_recursiva"&gt;función recursiva&lt;/a&gt;, es una función que se llama a si misma y controla cuando parar de hacerlo mediante una condición. Si esa condición no esta bien definida... a parte del cuelgue del hilo en cuestión lo más posible será terminar recibiendo una sonora &lt;a href="http://msdn.microsoft.com/es-es/library/system.stackoverflowexception(VS.80).aspx"&gt;StackOverflowException&lt;/a&gt;. &lt;/p&gt; &lt;p&gt;Para recorrer una estructura en arbol nada mejor que una función recursiva, un ejemplo muy simple es esta función que recorre todos los controles hijos de un control dado recursivamente:&lt;/p&gt; &lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;/// &amp;lt;summary&amp;gt;&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;&lt;span class="rem"&gt;/// Recorre recursivamente todos los&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;/// controles hijos de un control dado.&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;&lt;span class="rem"&gt;/// &amp;lt;/summary&amp;gt;&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="kwrd"&gt;void&lt;/span&gt; lookRecursive(Control Parent)&lt;/pre&gt;&lt;pre&gt;{&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="rem"&gt;// Recorro los subnodos&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;    &lt;span class="kwrd"&gt;foreach&lt;/span&gt; (Control child &lt;span class="kwrd"&gt;in&lt;/span&gt; Parent.Controls)&lt;/pre&gt;&lt;pre class="alt"&gt;    {&lt;/pre&gt;&lt;pre&gt;        Debug.Print(child.Name);&lt;/pre&gt;&lt;pre class="alt"&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;        &lt;span class="rem"&gt;// Si el subnodo tiene más subnodos&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;        &lt;span class="rem"&gt;// ejecuto recursivamente.&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;        &lt;span class="kwrd"&gt;if&lt;/span&gt; (child.Controls.Count &amp;gt; 0)&lt;/pre&gt;&lt;pre class="alt"&gt;            lookRecursive(child);&lt;/pre&gt;&lt;pre&gt;    }&lt;/pre&gt;&lt;pre class="alt"&gt;}&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Podemos hacer que la función nos&amp;nbsp;devuelva un elemento introduciendo una variable&amp;nbsp;para el almacenamiento,&amp;nbsp;si por ejemplo lo que queremos es que encuentre un determinado control por su nombre y lo devuelva (ya hay un método por ahí por la BCL que lo hace):&lt;/p&gt;
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;/// &amp;lt;summary&amp;gt;&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;&lt;span class="rem"&gt;/// Recorre recursivamente todos los&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;/// controles y encuentra el de un nombre&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;&lt;span class="rem"&gt;/// determinado.&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;/// &amp;lt;/summary&amp;gt;&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;Control findControl(Control Parent, String Name)&lt;/pre&gt;&lt;pre class="alt"&gt;{&lt;/pre&gt;&lt;pre&gt;    Control temp=&lt;span class="kwrd"&gt;null&lt;/span&gt;;&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="rem"&gt;// Recorro los subnodos&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;    &lt;span class="kwrd"&gt;foreach&lt;/span&gt; (Control child &lt;span class="kwrd"&gt;in&lt;/span&gt; Parent.Controls)&lt;/pre&gt;&lt;pre class="alt"&gt;    {&lt;/pre&gt;&lt;pre&gt;        &lt;span class="rem"&gt;// Criterio de búsqueda&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;        &lt;span class="kwrd"&gt;if&lt;/span&gt; (child.Name == Name)&lt;/pre&gt;&lt;pre&gt;            temp = child;&lt;/pre&gt;&lt;pre class="alt"&gt;        &lt;span class="kwrd"&gt;else&lt;/span&gt; &lt;span class="kwrd"&gt;if&lt;/span&gt;((temp==&lt;span class="kwrd"&gt;null&lt;/span&gt;) &amp;amp;&amp;amp; (child.Controls.Count &amp;gt; 0))&lt;/pre&gt;&lt;pre&gt;            temp = findControl(child,Name);&lt;/pre&gt;&lt;pre class="alt"&gt;    }&lt;/pre&gt;&lt;pre&gt;    &lt;span class="kwrd"&gt;return&lt;/span&gt; temp;&lt;/pre&gt;&lt;pre class="alt"&gt;}&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Ahora vamos a complicarlo un poco más añadiendo las siguientes características:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Adaptable a cualquier tipo de objetos: Usando &lt;a href="http://msdn.microsoft.com/es-es/library/512aeb7t(VS.80).aspx"&gt;genéricos&lt;/a&gt;. 
&lt;li&gt;Definir nuestro propio criterio de búsqueda: Pasando un &lt;a href="http://msdn.microsoft.com/es-es/library/bfcke1bz(VS.80).aspx"&gt;Predicate&lt;/a&gt; como argumento que contenga el criterio. 
&lt;li&gt;Definir como se obtienen los sub-nodos: Pasando un delegado que lo especifique. 
&lt;li&gt;La posibilidad de que el resultado no sea único: Devolviendo una colección ó array. 
&lt;li&gt;Poder parar de&amp;nbsp;recorrer cuando encontremos lo que queremos: Que la colección devuelta sea &lt;a href="http://msdn.microsoft.com/es-es/library/system.collections.ienumerable.aspx"&gt;IEnumerable&lt;/a&gt; ó &lt;a href="http://msdn.microsoft.com/es-es/library/9eekhta0.aspx"&gt;IEnumerable&amp;lt;T&amp;gt;&lt;/a&gt;y devolver con &lt;a href="http://msdn.microsoft.com/es-es/library/9k7k7cf0.aspx"&gt;yield&lt;/a&gt;.&lt;/li&gt;&lt;/ul&gt;
&lt;p&gt;Asi queda:&lt;/p&gt;
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="kwrd"&gt;delegate&lt;/span&gt; IEnumerable getChilds&amp;lt;T&amp;gt;(T Element);&lt;/pre&gt;&lt;pre&gt;IEnumerable&amp;lt;T&amp;gt; findRecursive&amp;lt;T&amp;gt;(T Parent, getChilds&amp;lt;T&amp;gt; Elements, Predicate&amp;lt;T&amp;gt; Criteria)&lt;/pre&gt;&lt;pre class="alt"&gt;{&lt;/pre&gt;&lt;pre&gt;    &lt;span class="kwrd"&gt;foreach&lt;/span&gt; (T element &lt;span class="kwrd"&gt;in&lt;/span&gt; Elements.Invoke(Parent))&lt;/pre&gt;&lt;pre class="alt"&gt;    {&lt;/pre&gt;&lt;pre&gt;        &lt;span class="kwrd"&gt;if&lt;/span&gt; (Criteria.Invoke(element))&lt;/pre&gt;&lt;pre class="alt"&gt;            &lt;span class="kwrd"&gt;yield&lt;/span&gt; &lt;span class="kwrd"&gt;return&lt;/span&gt; element;&lt;/pre&gt;&lt;pre&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;        &lt;span class="kwrd"&gt;foreach&lt;/span&gt; (T element2 &lt;span class="kwrd"&gt;in&lt;/span&gt; findRecursive&amp;lt;T&amp;gt;(element,Elements, Criteria))&lt;/pre&gt;&lt;pre&gt;            &lt;span class="kwrd"&gt;yield&lt;/span&gt; &lt;span class="kwrd"&gt;return&lt;/span&gt; element2;&lt;/pre&gt;&lt;pre class="alt"&gt;    }&lt;/pre&gt;&lt;pre&gt;}&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;El delegado getChilds define como obtener subnodos de un nodo dado.&lt;/p&gt;
&lt;p&gt;&lt;em&gt;Nota: En este ejemplo, en el delegado&amp;nbsp;devuelvo IEnumerable y no IEnumberable&amp;lt;T&amp;gt; (que seria lo lógico) porque&amp;nbsp;&lt;/em&gt;&lt;a href="http://msdn.microsoft.com/es-es/library/system.windows.forms.control.controls(VS.80).aspx"&gt;&lt;em&gt;Control.Controls&lt;/em&gt;&lt;/a&gt;&lt;em&gt; es un &lt;/em&gt;&lt;a href="http://msdn.microsoft.com/es-es/library/system.windows.forms.control.controls(VS.80).aspx"&gt;&lt;em&gt;ControlCollection&lt;/em&gt;&lt;/a&gt;&lt;em&gt; que solo implementa dicha interfaz, no la genérica :P&lt;/em&gt;&lt;/p&gt;
&lt;p&gt;Para usarlo... por ejemplo, queremos que todos los paneles pasen a tener borde &lt;em&gt;FixedSingle&lt;/em&gt;:&lt;/p&gt;
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;// Defino el criterio de búsqueda,&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;&lt;span class="rem"&gt;// en este caso, quiero los controles&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;// que sean paneles.&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;Predicate&amp;lt;Control&amp;gt; lookForPanels = &lt;span class="kwrd"&gt;delegate&lt;/span&gt;(Control c)&lt;/pre&gt;&lt;pre class="alt"&gt;{&lt;/pre&gt;&lt;pre&gt;    &lt;span class="kwrd"&gt;return&lt;/span&gt; c &lt;span class="kwrd"&gt;is&lt;/span&gt; Panel;&lt;/pre&gt;&lt;pre class="alt"&gt;};&lt;/pre&gt;&lt;pre&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;// Defino como obtengo los hijos de &lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;&lt;span class="rem"&gt;// este tipo de objeto.&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;getChilds&amp;lt;Control&amp;gt; getChildControls = &lt;span class="kwrd"&gt;delegate&lt;/span&gt;(Control C)&lt;/pre&gt;&lt;pre&gt;{&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="kwrd"&gt;return&lt;/span&gt; C.Controls;&lt;/pre&gt;&lt;pre&gt;};&lt;/pre&gt;&lt;pre class="alt"&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;&lt;span class="rem"&gt;// Por último efectuo la búsqueda&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;// y obtengo los resultados.&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;&lt;span class="kwrd"&gt;foreach&lt;/span&gt; (Panel c &lt;span class="kwrd"&gt;in&lt;/span&gt; findRecursive&amp;lt;Control&amp;gt;(&lt;span class="kwrd"&gt;this&lt;/span&gt;, getChildControls, lookForPanels))&lt;/pre&gt;&lt;pre class="alt"&gt;{&lt;/pre&gt;&lt;pre&gt;    c.BorderStyle = BorderStyle.FixedSingle;&lt;/pre&gt;&lt;pre class="alt"&gt;}&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Y si se quiere más complejo también se puede&amp;nbsp;&lt;a href="http://www.vtortola.net/post/Recorrer-una-estructura-en-arbol-con-multiples-hilos-ThreadedTreeBase.aspx"&gt;recorrer una estructura en arbol con múltiples hilos&lt;/a&gt;:P&lt;/p&gt;
&lt;h6&gt;&lt;a href="http://www.vtortola.net/post/Recursividad-y-yield-return-Haciendo-queries-a-colecciones-en-arbol-en-C-20.aspx"&gt;Recursividad y yield return. Haciendo queries a colecciones en arbol en C# 2.0 | vtortola.NET&lt;/a&gt;&lt;/h6&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=90794" width="1" height="1"&gt;</description><category domain="http://geeks.ms/blogs/vtortola/archive/tags/.NET+2.0/default.aspx">.NET 2.0</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/Gen_26002300_233_3B00_ricos/default.aspx">Gen&amp;#233;ricos</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/Interfaces/default.aspx">Interfaces</category></item><item><title>Listo para empezar a trabajar en Dublin</title><link>http://geeks.ms/blogs/vtortola/archive/2008/06/12/listo-para-empezar-a-trabajar-en-dublin.aspx</link><pubDate>Thu, 12 Jun 2008 20:19:44 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:88753</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>11</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=88753</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2008/06/12/listo-para-empezar-a-trabajar-en-dublin.aspx#comments</comments><description>&lt;p&gt;&lt;a href="http://www.datakraft.net/"&gt;&lt;img style="border-top-width:0px;border-left-width:0px;border-bottom-width:0px;margin:0px 20px 0px 15px;border-right-width:0px;" height="45" alt="datakraft" src="http://geeks.ms/blogs/vtortola/WindowsLiveWriter/ListoparaempezaratrabajarenDublin_12B29/datakraft_1.png" width="150" align="left" border="0" /&gt;&lt;/a&gt;Bueno pues las vacaciones se acaban&amp;nbsp;y es la hora de volver a trabajar y a .NET&amp;nbsp;:D El próximo día 23 me incorporo a &lt;a href="http://www.datakraft.net/"&gt;Datakraft&lt;/a&gt; en Dublín como desarrollador y debo confesar que estoy bastante excitado con el tema, voy a tener la oportunidad de sumergirme en .NET 3.5, desarrollo Windows/web/back-end y&amp;nbsp;metodologías ágiles.&lt;/p&gt; &lt;p&gt;Con esto&amp;nbsp;completo mi instalación en Dublín al 100%, después de 2 meses y medio aprendiendo inglés en el &lt;a href="http://www.lci.ie"&gt;LCI&lt;/a&gt;, encontrar casa y encontrar trabajo. Otro día contaré como ha sido el proceso a grandes rasgos, pero desde luego ha sido una aventura desde el primer día y sin lugar a dudas considero que fué una buena decisión, no solo por aprender inglés, si no por conocer gente de todo el mundo y la aventura del día a día defendiendote con lo poco que hablas y lo menos que entiendes. Ahora no hablo un inglés para tirar cohetes, pero suficiente para defenderme en el día a día (pero aún no entiendo &lt;em&gt;Los Simpson&lt;/em&gt; en inglés xD), espero que en un par de años hablar y entender sin ningún tipo de problemas.&lt;/p&gt; &lt;p&gt;Desde aquí me gustaria agradecer a mis antiguas empresas &lt;a href="http://www.avanade.com/es/"&gt;Avanade&lt;/a&gt; y &lt;a href="http://experianmarketingsolutions.com/"&gt;Experian&lt;/a&gt; por prestarse a dar referencias&amp;nbsp;a mi nueva empresa sobre mi y a mi ex-compañero de Avanade&amp;nbsp;Gerardo K.&amp;nbsp;por prestarse a escribir una referencia técnica recomendándome.&lt;/p&gt; &lt;p&gt;Ahora una semana para España... que echo de menos muchas cosas... :)&lt;/p&gt; &lt;h6&gt;&lt;a href="http://www.vtortola.net/post/Listo-para-empezar-a-trabajar-en-Dublin.aspx"&gt;Listo para empezar a trabajar en Dublin| vtortola.NET&lt;/a&gt;&lt;/h6&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=88753" width="1" height="1"&gt;</description><category domain="http://geeks.ms/blogs/vtortola/archive/tags/Personal/default.aspx">Personal</category></item><item><title>Un mal dia...</title><link>http://geeks.ms/blogs/vtortola/archive/2008/06/03/un-mal-dia.aspx</link><pubDate>Tue, 03 Jun 2008 21:14:18 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:87821</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>3</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=87821</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2008/06/03/un-mal-dia.aspx#comments</comments><description>&lt;p&gt;Voy preparándome psicológicamente para la vuelta al trabajo... xD&lt;/p&gt; &lt;p&gt;Unos cuantos videos de lo que seguro algún día se nos ha pasado por la cabeza hacer....&lt;/p&gt; &lt;p&gt;&lt;embed src="http://www.youtube.com/v/jlxSUuGB2Do&amp;amp;hl=es" width="425" height="355" type="application/x-shockwave-flash" wmode="transparent"&gt;&lt;/embed&gt;&lt;br /&gt;&lt;br /&gt;&lt;embed src="http://www.youtube.com/v/9toErknT1jY&amp;amp;hl=es" width="425" height="355" type="application/x-shockwave-flash" wmode="transparent"&gt;&lt;/embed&gt;&lt;br /&gt;&lt;br /&gt;&lt;embed src="http://www.youtube.com/v/IzBy6agXKoA&amp;amp;hl=es" width="425" height="355" type="application/x-shockwave-flash" wmode="transparent"&gt;&lt;/embed&gt;&lt;br /&gt;&lt;br /&gt;&lt;embed src="http://www.youtube.com/v/buiq_mMjhQY&amp;amp;hl=es" width="425" height="355" type="application/x-shockwave-flash" wmode="transparent"&gt;&lt;/embed&gt; &lt;br /&gt;&lt;br /&gt;&lt;/p&gt; &lt;p&gt;En verdad estoy deseando volver a trabajar... pero voy a disfrutar las últimas semenas de felicidad :D&lt;/p&gt; &lt;h6&gt;&lt;a href="http://www.vtortola.net/post/Un-mal-dia.aspx"&gt;Un mal dia... | vtortola.NET&lt;/a&gt;&lt;/h6&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=87821" width="1" height="1"&gt;</description><category domain="http://geeks.ms/blogs/vtortola/archive/tags/Humor/default.aspx">Humor</category></item><item><title>Pooling de llamadas asincronas</title><link>http://geeks.ms/blogs/vtortola/archive/2008/05/30/pooling-de-llamadas-asincronas.aspx</link><pubDate>Fri, 30 May 2008 16:24:12 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:87394</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>0</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=87394</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2008/05/30/pooling-de-llamadas-asincronas.aspx#comments</comments><description>&lt;p&gt;Hora de volver a trabajar... asi que toca quitarle el polvo al Visual Studio que tenia abandonado ya estos meses, la buena vida se acaba... xD&lt;/p&gt; &lt;p&gt;En determinadas ocasiones, necesitamos lanzar un cierto número de ejecuciones en paralelo y esperar a que terminen todas para devolver el resultado final. Existen diversas formas de hacerlo, y yo voy a poner la que, después de darle un par de vueltas... me parece la mejor y más sencilla, ... se puede hacer aún mejor, pero no se si más sencilla... y no se si lo que se puede mejorar merece la pena en cuanto a la complejidad que añade.&lt;/p&gt; &lt;p&gt;Un ejemplo práctico, este método pertenece a una clase que estoy programando para realizar pruebas de estres y carga, la clase tiene una lista de clientes y cuando se ejecuta esta función ejecuta el delegado que se pasa como argumento en paralelo en todos los clientes a la vez, recolecta las excepciones capturadas y las devuelve como una lista. Por supuesto, tiene que esperar a que terminen todas las pruebas en paralelo para poder devolver la lista :P&lt;/p&gt; &lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="kwrd"&gt;private&lt;/span&gt; List&amp;lt;Exception&amp;gt; test(Int32 Times, Int32 Interval, TestDlg_ Test)&lt;/pre&gt;&lt;pre&gt;{&lt;/pre&gt;&lt;pre class="alt"&gt;    List&amp;lt;Exception&amp;gt; errors = &lt;span class="kwrd"&gt;new&lt;/span&gt; List&amp;lt;Exception&amp;gt;();&lt;/pre&gt;&lt;pre&gt;    List&amp;lt;IAsyncResult&amp;gt; working = &lt;span class="kwrd"&gt;new&lt;/span&gt; List&amp;lt;IAsyncResult&amp;gt;();&lt;/pre&gt;&lt;pre class="alt"&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;    &lt;span class="kwrd"&gt;lock&lt;/span&gt; (working) &lt;span class="rem"&gt;// Bloqueo hasta que lanze todos los clientes&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;    {&lt;/pre&gt;&lt;pre&gt;        &lt;span class="kwrd"&gt;foreach&lt;/span&gt; (IImApplicationClient client &lt;span class="kwrd"&gt;in&lt;/span&gt; &lt;span class="kwrd"&gt;this&lt;/span&gt;.Clients)&lt;/pre&gt;&lt;pre class="alt"&gt;        {&lt;/pre&gt;&lt;pre&gt;            working.Add(Test.BeginInvoke(client, Times, Interval,&lt;/pre&gt;&lt;pre class="alt"&gt;                &lt;span class="kwrd"&gt;delegate&lt;/span&gt;(IAsyncResult IA)&lt;/pre&gt;&lt;pre&gt;                {&lt;/pre&gt;&lt;pre class="alt"&gt;                    &lt;span class="kwrd"&gt;try&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;                    {&lt;/pre&gt;&lt;pre class="alt"&gt;                        Test.EndInvoke(IA);&lt;/pre&gt;&lt;pre&gt;                        &lt;span class="kwrd"&gt;lock&lt;/span&gt; (working)&lt;/pre&gt;&lt;pre class="alt"&gt;                        {&lt;/pre&gt;&lt;pre&gt;                            working.Remove(IA);         &lt;span class="rem"&gt;// Lo elimino de la lista,&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;                            &lt;span class="kwrd"&gt;if&lt;/span&gt; (working.Count == 0)     &lt;span class="rem"&gt;// y si era el último...&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;                                Monitor.Pulse(working); &lt;span class="rem"&gt;// envio pulso para liberar&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;                        }                               &lt;span class="rem"&gt;// la espera&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;                    }&lt;/pre&gt;&lt;pre class="alt"&gt;                    &lt;span class="kwrd"&gt;catch&lt;/span&gt; (Exception ex)&lt;/pre&gt;&lt;pre&gt;                    {&lt;/pre&gt;&lt;pre class="alt"&gt;                        IImApplicationClient asynClient =&lt;/pre&gt;&lt;pre&gt;                            IA.AsyncState &lt;span class="kwrd"&gt;as&lt;/span&gt; IImApplicationClient;&lt;/pre&gt;&lt;pre class="alt"&gt;                        &lt;span class="kwrd"&gt;lock&lt;/span&gt;(errors)&lt;/pre&gt;&lt;pre&gt;                            errors.Add(&lt;span class="kwrd"&gt;new&lt;/span&gt; Exception&lt;/pre&gt;&lt;pre class="alt"&gt;                                (client != &lt;span class="kwrd"&gt;null&lt;/span&gt; ? asynClient.Id : &lt;span class="str"&gt;&amp;quot;Id unknown.&amp;quot;&lt;/span&gt;, ex));&lt;/pre&gt;&lt;pre&gt;                    }&lt;/pre&gt;&lt;pre class="alt"&gt;                }, client));&lt;/pre&gt;&lt;pre&gt;        }&lt;/pre&gt;&lt;pre class="alt"&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;        &lt;span class="kwrd"&gt;if&lt;/span&gt; (working.Count &amp;gt; 0) &lt;span class="rem"&gt;// Si se han lanzado clientes...&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;            Monitor.Wait(working); &lt;span class="rem"&gt;// bloqueo en espera.&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;    }&lt;/pre&gt;&lt;pre class="alt"&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;    &lt;span class="kwrd"&gt;return&lt;/span&gt; errors;&lt;/pre&gt;&lt;pre class="alt"&gt;}&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;El planteamiento es el siguiente:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Se usa una lista para tener controladas las llamadas asíncronas. 
&lt;li&gt;Cada vez que se lanza una llamada asíncrona, el IAsyncResult resultante se añade a la lista. 
&lt;li&gt;Se bloquea la lista hasta que todas han sido lanzadas, y si se ha lanzado más de una, se ejecuta un Monitor.Wait para que se detenga la ejecución ahí hasta que se realize un Monitor.Pulse. 
&lt;li&gt;Cada vez que una llamada asíncrona termina, se elimina su IAsyncResult de la lista. 
&lt;li&gt;Si el IAsyncResult es el último que quedaba, se realiza un Monitor.Pulse para que la ejecución pueda seguir puesto que ya finalizaron todas las llamadas asíncronas.&lt;/li&gt;&lt;/ul&gt;
&lt;p&gt;Sugerencias, como siempre, bienvenidas :D&lt;/p&gt;
&lt;h6&gt;&lt;a href="http://www.vtortola.net/post/Pooling-de-llamadas-asincronas.aspx"&gt;Pooling de llamadas asincronas| vtortola.NET&lt;/a&gt;&lt;/h6&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=87394" width="1" height="1"&gt;</description><category domain="http://geeks.ms/blogs/vtortola/archive/tags/.NET+2.0/default.aspx">.NET 2.0</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/Excepciones/default.aspx">Excepciones</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/C_2300_+2.0/default.aspx">C# 2.0</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/multithreading/default.aspx">multithreading</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/sincronizaci_26002300_243_3B00_n/default.aspx">sincronizaci&amp;#243;n</category></item><item><title>Visual Basic .NET vs C# .NET: ¿Cual es mejor y por que?</title><link>http://geeks.ms/blogs/vtortola/archive/2008/05/06/visual-basic-net-vs-c-net-191-cual-es-mejor-y-por-que.aspx</link><pubDate>Tue, 06 May 2008 13:30:24 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:84912</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>1</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=84912</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2008/05/06/visual-basic-net-vs-c-net-191-cual-es-mejor-y-por-que.aspx#comments</comments><description>&lt;p&gt;&lt;strong&gt;&lt;img style="margin:0px 30px 15px 0px;" height="266" src="http://www.secondnug.com/img/eventos/carteles/c04_VBC.jpg" width="360" align="left" alt="" /&gt; Hoy&lt;/strong&gt; Second Nug tiene el honor de presentar a dos ponentes de excepción, &lt;strong&gt;Guillermo Som&lt;/strong&gt; (&lt;a href="http://www.elguille.info/"&gt;el Guille&lt;/a&gt;) y &lt;strong&gt;Marino Posadas&lt;/strong&gt; (&lt;a href="http://www.elavefenix.net/"&gt;el Ave Fénix&lt;/a&gt;), en la que será una gran batalla donde dos voces con gran experiencia expondrán sus mejores bazas en un duelo sin igual: &lt;strong&gt;VB .NET vs C# .NET&lt;/strong&gt;.&lt;br /&gt;Sabremos por qué se decantaron por un lenguaje u otro y nos presentarán su evolución en las nuevas versiones del .NET Framework. Nos desvelaran secretos y trucos de sus defendidos y veremos si es cierto aquello de que lo que se puede hacer con uno, se puede realmente hacer con el otro.&lt;br /&gt;Además los asistentes podrán resolver sus dudas preguntando a nuestros expertos y participar en el resultado final de la contienda.&lt;br /&gt;El eterno dilema al descubierto. ¿Quién será el vencedor?  &lt;p&gt;El evento será a las &lt;strong&gt;19:30 - 21:30 (GMT+2),&lt;/strong&gt; y como en las anteriores ocasiones, se retransmitirá vía Web a través de Live Meeting.  &lt;p&gt;Si no tienes &lt;em&gt;Live Meeting&lt;/em&gt;, puedes descargarlo en el siguiente &lt;a href="http://office.microsoft.com/en-us/help/HA101733831033.aspx"&gt;&lt;strong&gt;enlace&lt;/strong&gt;&lt;/a&gt;.  &lt;p&gt;&lt;strong&gt;Podéis&amp;nbsp;registraros en el evento en el siguiente &lt;a href="http://msevents.microsoft.com/CUI/WebCastEventDetails.aspx?EventID=1032374810&amp;amp;EventCategory=4&amp;amp;culture=es-ES&amp;amp;CountryCode=ES"&gt;enlace&lt;/a&gt;.&lt;/strong&gt;&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=84912" width="1" height="1"&gt;</description></item><item><title>Trabajando con el registro de Windows desde C# y .NET</title><link>http://geeks.ms/blogs/vtortola/archive/2008/03/27/trabajando-con-el-registro-de-windows-desde-c-y-net.aspx</link><pubDate>Wed, 26 Mar 2008 23:53:12 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:81738</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>3</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=81738</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2008/03/27/trabajando-con-el-registro-de-windows-desde-c-y-net.aspx#comments</comments><description>&lt;p&gt;Manejar el registro de Windows es algo... en parte tedioso por lo extenso y medianamente documentado que esta lo que contiene. En mi humilde opinión, es algo a evitar siempre que sea posible en virtud de los archivos de configuración; pero en ocasiones necesitamos crear/modificar entradas que afectan al funcionamiento de otros programas ó del propio Windows desde nuestras aplicaciones,&amp;nbsp;asi que&amp;nbsp;hay que arremangarse y meterle mano :D&lt;/p&gt; &lt;p&gt;Primero un pequeño repaso de como se estructura la información a&amp;nbsp;grandes rasgos.&amp;nbsp;Podemos ver el registro mediante la aplicación regedit.exe. Encontramos 5 elementos principales, que así por encima vienen a ser:&lt;/p&gt; &lt;ul&gt; &lt;li&gt;&lt;strong&gt;HKEY_CLASSES_ROOT&lt;/strong&gt; (HKCR)&amp;nbsp;: Contiene las realciones entre los identificadores de programa y clases que se usan por COM+, asociaciones de archivo e información de ejecución de aplicaciones.  &lt;li&gt;&lt;strong&gt;HKEY_USERS&lt;/strong&gt; (HKU)&amp;nbsp;: Contiene un elemento por cada usuario del sistema y en cada uno se almacenan sus preferencias y configuraciones individuales.  &lt;li&gt;&lt;strong&gt;HKEY_CURRENT_USER&lt;/strong&gt; (HKCU)&amp;nbsp;: Es como un enlace simbólico a la entrada en HKU correspondiente al usuario actual.  &lt;li&gt;&lt;strong&gt;HKEY_LOCAL_MACHINE&lt;/strong&gt; (HKLM)&amp;nbsp;: Información del sistema y del hardware.  &lt;li&gt;&lt;strong&gt;HKEY_CURRENT_CONFIG&lt;/strong&gt; (HKCC) : Es como un enlace simbólico a la entrada&amp;nbsp;en&amp;nbsp;HKLM correspondiente a la configuración hardware actual.&lt;/li&gt;&lt;/ul&gt; &lt;p&gt;La información esta estructurada en forma de arbol mediante claves y valores. Las claves son como carpetas que puede contener otras claves, y los valores son una pareja key-value donde podemos asignar un valor. Los valores pueden ser de tipo:&lt;/p&gt; &lt;ul&gt; &lt;li&gt;&lt;strong&gt;REG_DWORD&lt;/strong&gt; :&amp;nbsp;Número de 4 bytes, se usa para almacenar valores boleanos.  &lt;li&gt;&lt;strong&gt;REG_BINARY&lt;/strong&gt; :&amp;nbsp;Almacena datos binarios.  &lt;li&gt;&lt;strong&gt;REG_SZ&lt;/strong&gt; :&amp;nbsp;Cadena de texto.  &lt;li&gt;&lt;strong&gt;REG_MULTI_SZ&lt;/strong&gt; :&amp;nbsp;Almacena arrays de strings.  &lt;li&gt;&lt;strong&gt;REG_EXPAND_SZ&lt;/strong&gt; :&amp;nbsp;Almacena una variable en formato de string.&lt;/li&gt;&lt;/ul&gt; &lt;p&gt;Ahora vamos a meterle mano, lo primero que necesitamos es el namespace &lt;a href="http://msdn2.microsoft.com/en-us/library/microsoft.win32.aspx"&gt;Microsoft.Win32&lt;/a&gt; , y nuestras clases para trabajar serán&amp;nbsp;&lt;a href="http://msdn2.microsoft.com/en-us/library/microsoft.win32.registry.aspx"&gt;Registry&lt;/a&gt; y&amp;nbsp;&lt;a href="http://msdn2.microsoft.com/en-us/library/microsoft.win32.registrykey.aspx"&gt;RegistryKey&lt;/a&gt;. Lo primero, es llegar donde vamos a trabajar:  &lt;p&gt;&amp;nbsp;  &lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;// Abrimos la clave del registro con la que queremos trabajar&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;RegistryKey rk1 = Registry.LocalMachine;&lt;/pre&gt;&lt;pre class="alt"&gt;&amp;nbsp;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Trabajando con claves: 
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;// Nos movemos hasta la subclave donde queremos trabajar.&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;&lt;span class="rem"&gt;// El parámetro boleano indica si la abrimos en solo lectura (false)&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;// ó en lectura/escritura (true).&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;rk1 = rk1.OpenSubKey(&lt;span class="str"&gt;@&amp;quot;SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon&amp;quot;&lt;/span&gt;,&lt;span class="kwrd"&gt;true&lt;/span&gt;);&lt;/pre&gt;&lt;pre class="alt"&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;&lt;span class="rem"&gt;// Si devuelve null es que la clave no existe&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="kwrd"&gt;if&lt;/span&gt; (rk1 == &lt;span class="kwrd"&gt;null&lt;/span&gt;)&lt;/pre&gt;&lt;pre&gt;    Console.WriteLine(&lt;span class="str"&gt;&amp;quot;No existe esa clave&amp;quot;&lt;/span&gt;);&lt;/pre&gt;&lt;pre class="alt"&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;&lt;span class="rem"&gt;// Crear una nueva clave&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;// El método devuelve un RegistryKey apuntando&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;&lt;span class="rem"&gt;// a la nueva entrada.&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;RegistryKey rk2 = rk1.CreateSubKey(&lt;span class="str"&gt;&amp;quot;Prueba&amp;quot;&lt;/span&gt;);&lt;/pre&gt;&lt;pre&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;// Obtener todas las subclaves contenidas en esta:&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;String[] subKeys = rk1.GetSubKeyNames();&lt;/pre&gt;&lt;pre class="alt"&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;&lt;span class="rem"&gt;// Borrar una clave vacia:&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;rk.DeleteSubKey(&lt;span class="str"&gt;&amp;quot;Prueba&amp;quot;&lt;/span&gt;);&lt;/pre&gt;&lt;pre&gt;                &lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;// Borrar una clave recursivamente:&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;rk.DeleteSubKeyTree(&lt;span class="str"&gt;&amp;quot;Prueba&amp;quot;&lt;/span&gt;);&lt;/pre&gt;&lt;pre&gt;&amp;nbsp;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Trabajando con key-values: 
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;// Crea un key-value indicando su nombre, valor y tipo:&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;rk2.SetValue(&lt;span class="str"&gt;&amp;quot;ValorPrueba&amp;quot;&lt;/span&gt;, 0,RegistryValueKind.String);&lt;/pre&gt;&lt;pre class="alt"&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;&lt;span class="rem"&gt;// Obtener todos los nombres de key-values que hay en una clave:&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;String[] values = rk2.GetValueNames();&lt;/pre&gt;&lt;pre&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;// Obtener el valor de un key-value:&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;Console.WriteLine(rk2.GetValueKind(&lt;span class="str"&gt;&amp;quot;ValorPrueba&amp;quot;&lt;/span&gt;).ToString());&lt;/pre&gt;&lt;pre class="alt"&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;&lt;span class="rem"&gt;// Obtener el tipo de dato de registro &lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;// que contiene un key-value:&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;RegistryValueKind rvk = rk2.GetValueKind(&lt;span class="str"&gt;&amp;quot;ValorPrueba&amp;quot;&lt;/span&gt;);&lt;/pre&gt;&lt;pre class="alt"&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;&lt;span class="rem"&gt;// Borrar un key-value:&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="rem"&gt;// El parámetro boleano indica que salte una excepción&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;&lt;span class="rem"&gt;// si el key-value a borrar no existe.&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;p&gt;rk2.DeleteValue(&lt;span class="str"&gt;&amp;quot;ValorPrueba&amp;quot;&lt;/span&gt;, &lt;span class="kwrd"&gt;true&lt;/span&gt;);&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Aunque los &lt;em&gt;Setup Project&lt;/em&gt; que creamos con &lt;em&gt;Visual Studio&lt;/em&gt; tiene capacidad para añadir claves y key-values al registro, su funcionalidad esta muy limitada, por ejemplo... no podriamos crear un key-value que contuviese el path de la aplicación que estemos instalando a no ser que lo pusieramos harcodeado. &lt;/p&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;h6&gt;&lt;a href="http://www.vtortola.net/post/Trabajando-con-el-registro-de-Windows-desde-C-y-NET.aspx"&gt;Trabajando con el registro de Windows desde C# y .NET | vtortola.NET&lt;/a&gt;&lt;/h6&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=81738" width="1" height="1"&gt;</description><category domain="http://geeks.ms/blogs/vtortola/archive/tags/.NET+2.0/default.aspx">.NET 2.0</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/C_2300_+2.0/default.aspx">C# 2.0</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/Windows/default.aspx">Windows</category></item><item><title>Evento: Windows Communication Foundation al Descubierto en SNUG</title><link>http://geeks.ms/blogs/vtortola/archive/2008/03/26/evento-windows-communication-foundation-al-descubierto-en-snug.aspx</link><pubDate>Wed, 26 Mar 2008 08:34:00 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:81672</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>4</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=81672</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2008/03/26/evento-windows-communication-foundation-al-descubierto-en-snug.aspx#comments</comments><description>&lt;p&gt;&lt;a href="http://www.secondnug.com/Eventos/tabid/57/Default.aspx"&gt;&lt;img src="http://www.vtortola.net/images/snug/snug_wcf.jpg" alt="" align="" border="" height="" hspace="" width="" /&gt;&lt;/a&gt;  &lt;/p&gt;&lt;p&gt;El próximo &lt;b&gt;1 de Abril&lt;/b&gt; podréis asistir a un nuevo Webcast en el que podréis sacar el máximo provecho de sistemas, tanto nuevos como ya existentes, a través de &lt;b&gt;Windows Communication Foundation&lt;/b&gt;. Para esta nueva charla, contaremos con la presencia de &lt;b&gt;Hadi Hariri&lt;/b&gt; como ponente de excepción, que nos deleitará con todo lo que esta nueva herramienta nos puede ofrecer.  &lt;/p&gt;&lt;p&gt;El evento será a las &lt;b&gt;19:30 - 21:30 (GMT+1),&lt;/b&gt; y como en las anteriores ocasiones, se retransmitirá vía Web a través de Live Meeting.  &lt;/p&gt;&lt;ul&gt; &lt;li&gt;Si no tienes &lt;i&gt;Live Meeting&lt;/i&gt;, puedes descargarlo en el siguiente &lt;a href="http://office.microsoft.com/en-us/help/HA101733831033.aspx"&gt;&lt;b&gt;enlace&lt;/b&gt;&lt;/a&gt;.  &lt;/li&gt;&lt;li&gt;&lt;b&gt;Podéis&amp;nbsp;registraros en el evento en el siguiente &lt;a href="http://msevents.microsoft.com/CUI/EventDetail.aspx?EventID=1032374581&amp;amp;Culture=es-ES"&gt;enlace&lt;/a&gt;.&lt;/b&gt;&lt;/li&gt;&lt;/ul&gt; &lt;p&gt;Yo para variar, me lo perderé en directo&amp;nbsp;porque será mi segundo día en Dublin y tengo clase hasta las 19:00, pero lo bueno de estos eventos es poderlos ver a posteriori en diferido :D&amp;nbsp;y este en concreto me interesa muchísimo.&lt;/p&gt;&lt;p&gt;&lt;a href="http://meneame.net/story/net-evento-online-windows-communication-foundation-fondo/voters"&gt;&lt;b&gt;Menealó&lt;/b&gt;&lt;/a&gt;&lt;/p&gt;&lt;h6&gt;&lt;a href="http://www.vtortola.net/post/Evento-Windows-Communication-Foundation-al-Descubierto-en-SNUG.aspx"&gt;Evento: Windows Communication Foundation al Descubierto en SNUG | vtortola.NET&lt;/a&gt;&lt;/h6&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=81672" width="1" height="1"&gt;</description><category domain="http://geeks.ms/blogs/vtortola/archive/tags/wcf/default.aspx">wcf</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/snug/default.aspx">snug</category></item><item><title>Chatarra a precio de oro III, Microsoft es asi</title><link>http://geeks.ms/blogs/vtortola/archive/2008/03/24/chatarra-a-precio-de-oro-iii-microsoft-es-asi.aspx</link><pubDate>Mon, 24 Mar 2008 19:47:50 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:81580</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>6</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=81580</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2008/03/24/chatarra-a-precio-de-oro-iii-microsoft-es-asi.aspx#comments</comments><description>&lt;p&gt;Y no se confundan, Microsoft nada pinta aquí... al menos para mi, pero si para el SAT :D&amp;nbsp; Sigo con mi lucha con la chatarra (&lt;a href="http://www.vtortola.net/post/Chatarra-a-precio-de-oro.aspx" target="_blank"&gt;parte I&lt;/a&gt;, &lt;a href="http://www.vtortola.net/post/Chatarra-a-precio-de-oro-II.aspx" target="_blank"&gt;parte II&lt;/a&gt;), alcanzado ahora nuevas cotas de asombro con el SAT. Una de mis reglas cuando hablo con el SAT, es ser tan humilde como pueda, prestar atención a lo que dice y evitar dar a entender que soy un usuario avanzado, en este caso... mucho menos decir que soy programador.&lt;/p&gt; &lt;p&gt;Una vez instalada la aplicación en red,&amp;nbsp;la primera cosa que se me ocurre (yo y mis ocurrencias...), es lanzar el cliente como usuario Invitado ... a lo que recibo un error de que no puede escribir a un archivo que el programa de instalación ha dejado caer en &lt;strong&gt;C:\&lt;/strong&gt; ... nada más y nada menos, no se me ocurre otra cosa que llamar al SAT (más ocurrencias bobas...) para preguntar como ejecutar la aplicación con una cuenta desprivilegiada para que nadie pueda cargarse la máquina... la respuesta... increible:&lt;/p&gt; &lt;p&gt;&lt;em&gt;&amp;quot;... es así y la aplicación necesita que se ejecute como administrador, es un requerimiento de Microsoft... es lo que hay...&amp;quot;&amp;nbsp; [ ... ] &amp;quot;... vamos... deberia ser un usuario malintencionado...&amp;quot;&lt;/em&gt;&lt;/p&gt; &lt;p&gt;Aún estoy recuperandome del sock. Bien, pues siguiendo los consejos de Josue en &lt;a href="http://www.geeks.ms" target="_blank"&gt;Geeks.ms&lt;/a&gt; y mi colega&amp;nbsp;&lt;a href="http://www.bandaancha.st/usuario.php?nick=Joe_Dalton" target="_blank"&gt;Joe_Dalton&lt;/a&gt; de &lt;a href="http://www.bandaancha.st" target="_blank"&gt;BandaAncha.st&lt;/a&gt; me lanzo a crear una Windows shell para contener al usuario en una interfaz de la que no puedan ejecutar nada, además deshabilito el Task Manager, ahora parece que todo irá bien y no hay posibilidad de catástrofe ya que los ordenadores no tienen teclado tampoco.&lt;/p&gt; &lt;p&gt;Comienzan los problemas de verdad, sin saber porque ... se cuelga &amp;quot;algo&amp;quot; en el servidor. Los clientes siguen funcionando, es decir... siguen accediendo a la bd en forma de archivos que hay en el recurso compartido y trabajando normalmente, pero en el servidor es imposible abrir el módulo de gestión ni abrir la aplicación cliente, obtengo errores de timeout y procesos colgados indefinidadmente, tampoco funciona el BDE Administrator del panel de control, nos vemos obligados a reiniciar la máquina... y vuelve a funcionar. Llamo al SAT (iluso yo) ... simplemente para preguntar como solventar el problema sin reiniciar la máquina, ya que eso supone que los clientes pierdan el trabajo no guardado ó hacerles que terminen, paren, reiniciar y volver a abrir de nuevo... con la mala imagen que da eso, es decir... que me diga algún servicio de Borland&amp;nbsp;que reniciar ... no sé... algo xD, la respuesta tan asombrosa ó más como la anterior:&lt;/p&gt; &lt;p&gt;&lt;em&gt;&amp;quot;... Microsoft no proveé de ninguna herramienta para hacer eso, es lo mismo que si se te cuelga alguna aplicación y tienes que reiniciar, no se puede hacer nada, Microsoft es así...&amp;quot;&lt;/em&gt;&lt;/p&gt; &lt;p&gt;Intentando recuperar la respiración,&amp;nbsp;me reincorporo, me sacudo el polvo de la ropa después de haber rodado varias veces por el suelo y vuelvo a sentarme en la silla de nuevo, minutos después me llaman de la sala diciendo que hay un equipo que &amp;quot;no va&amp;quot;. Me acerco y un mensaje alerta algo como&amp;nbsp;&lt;em&gt;&amp;quot;Cannot set focus on a unexistent window&amp;quot;&lt;/em&gt;, doy a aceptar y la pantalla se queda sin datos... y sin que funcione ningún botón, toca matarla y reiniciarla. Llamo al SAT de nuevo ... &amp;quot;hola, soy el de antes&amp;quot;, la respuesta... ya para llorar:&lt;/p&gt; &lt;p&gt;&lt;em&gt;&amp;quot;... eso es porque el usuario va muy rápido, cuando se inicia el test sale una ventana de bienvenida y hay que darle a aceptar, si se pulsa sobre la ventana de fondo sin darle a aceptar... pasa eso..., la ventana esa se puso para ese fin, que terminase de cargar la otra... si le das antes ... pues normal que se quede asi...&amp;quot;&lt;/em&gt;&lt;/p&gt; &lt;p&gt;En fin... Ahora mismo, mientras escribo esto estaba esperando a que el SAT me coja de nuevo el teléfono porque hay otro cliente que se ha quedado ... literalmente congelado, ni el cronómetro que hay en una de las esquinas corre... pero justo ahora mismo, después de 5min congelado ha saltado el error : &amp;quot;Lock time out, table xxx.db&amp;quot; ...&lt;/p&gt; &lt;p&gt;¿Alguien tiene idea de que se puede hacer? Han transcurrido los 15 días de prueba ya... con lo que no creo que se pueda devolver... pero una cosa es que no te guste, otra cosa es ... ESTO.&amp;nbsp; Este post se va a hacer interminable xD, ahora mismo estoy sacando un captura de pantalla de un volcado de datos (ó eso parece) sobre el formulario después de otro error de &amp;quot;Lock time out&amp;quot;. No sé si reir ó llorar...&lt;/p&gt; &lt;p&gt;&lt;a href="http://geeks.ms/blogs/vtortola/WindowsLiveWriter/ChatarraapreciodeoroIIIMicrosoftesasi_123AC/Locktimeoutyvolcado.jpg"&gt;&lt;img style="border-top-width:0px;border-left-width:0px;border-bottom-width:0px;border-right-width:0px;" height="179" alt="Locktimeoutyvolcado" src="http://geeks.ms/blogs/vtortola/WindowsLiveWriter/ChatarraapreciodeoroIIIMicrosoftesasi_123AC/Locktimeoutyvolcado_thumb.jpg" width="240" border="0" /&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;Aquí queda el testimonio de mi indignación e impotencia&amp;nbsp;:(&lt;/p&gt; &lt;p&gt;&amp;nbsp;&lt;/p&gt; &lt;h6&gt;&lt;a href="http://www.vtortola.net/post/Chatarra-a-precio-de-oro-III%2c-Microsoft-es-asi.aspx"&gt;Chatarra a precio de oro III, Microsoft es asi | vtortola.NET&lt;/a&gt;&lt;/h6&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=81580" width="1" height="1"&gt;</description></item><item><title>Forzando la captura de excepciones no manejadas en WPF</title><link>http://geeks.ms/blogs/vtortola/archive/2008/03/19/forzando-la-captura-de-excepciones-no-manejadas-en-wpf.aspx</link><pubDate>Wed, 19 Mar 2008 22:21:23 GMT</pubDate><guid isPermaLink="false">2a2e7ade-7474-448b-9de5-1515d8bb7d1b:81335</guid><dc:creator>Valeriano Tórtola</dc:creator><slash:comments>1</slash:comments><wfw:commentRss>http://geeks.ms/blogs/vtortola/rsscomments.aspx?PostID=81335</wfw:commentRss><comments>http://geeks.ms/blogs/vtortola/archive/2008/03/19/forzando-la-captura-de-excepciones-no-manejadas-en-wpf.aspx#comments</comments><description>&lt;p&gt;En .NET 2.0 y WinForms había &lt;a href="http://geeks.ms/blogs/elbruno/archive/2007/05/05/en-contra-de-la-cruz-roja.aspx"&gt;una forma&lt;/a&gt; que ahora ya no es del todo válida en &lt;a href="http://msdn2.microsoft.com/es-es/library/ms754130.aspx"&gt;WPF&lt;/a&gt; ya que han desaparecido el método &lt;a href="http://msdn2.microsoft.com/es-es/library/system.windows.forms.application.setunhandledexceptionmode.aspx"&gt;Application.SetUnhandledExceptionMode&lt;/a&gt; y el evento &lt;a href="http://msdn2.microsoft.com/en-us/library/system.windows.forms.application.threadexception.aspx"&gt;Application.ThreadException&lt;/a&gt;, en su lugar tenemos &lt;a href="http://msdn2.microsoft.com/es-es/library/system.windows.application.dispatcherunhandledexception.aspx"&gt;Application.DispatcherUnhandledException&lt;/a&gt;:&lt;/p&gt; &lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="kwrd"&gt;&amp;lt;&lt;/span&gt;&lt;span class="html"&gt;Application&lt;/span&gt; &lt;span class="attr"&gt;x:Class&lt;/span&gt;&lt;span class="kwrd"&gt;=&amp;quot;KiosimWPF.App&amp;quot;&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;    &lt;span class="attr"&gt;xmlns&lt;/span&gt;&lt;span class="kwrd"&gt;=&amp;quot;http://schemas.microsoft.com/winfx/2006/xaml/presentation&amp;quot;&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="attr"&gt;xmlns:x&lt;/span&gt;&lt;span class="kwrd"&gt;=&amp;quot;http://schemas.microsoft.com/winfx/2006/xaml&amp;quot;&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;    &lt;span class="attr"&gt;StartupUri&lt;/span&gt;&lt;span class="kwrd"&gt;=&amp;quot;Window1.xaml&amp;quot;&lt;/span&gt; &lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="attr"&gt;DispatcherUnhandledException&lt;/span&gt;&lt;span class="kwrd"&gt;=&amp;quot;App_DispatcherUnhandledException&amp;quot;&lt;/span&gt;&lt;span class="kwrd"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;    &lt;span class="kwrd"&gt;&amp;lt;&lt;/span&gt;&lt;span class="html"&gt;Application.Resources&lt;/span&gt;&lt;span class="kwrd"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;         &lt;/pre&gt;&lt;pre&gt;    &lt;span class="kwrd"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="html"&gt;Application.Resources&lt;/span&gt;&lt;span class="kwrd"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;&lt;span class="kwrd"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="html"&gt;Application&lt;/span&gt;&lt;span class="kwrd"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Luego en el handler del evento podemos evitar que la excepción tumbe la aplicación:&lt;/p&gt;
&lt;div class="csharpcode"&gt;&lt;pre class="alt"&gt;&lt;span class="kwrd"&gt;void&lt;/span&gt; App_DispatcherUnhandledException(&lt;span class="kwrd"&gt;object&lt;/span&gt; sender, DispatcherUnhandledExceptionEventArgs e)&lt;/pre&gt;&lt;pre&gt;{&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="rem"&gt;// Proceso la excepción:&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;    Trace.Write(String.Format(&lt;span class="str"&gt;&amp;quot;({0}):{1}\n\n{2}&amp;quot;&lt;/span&gt;,e.Exception.GetType().Name,&lt;/pre&gt;&lt;pre class="alt"&gt;                                            e.Exception.Message,&lt;/pre&gt;&lt;pre&gt;                                            e.Exception.StackTrace));&lt;/pre&gt;&lt;pre class="alt"&gt;&amp;nbsp;&lt;/pre&gt;&lt;pre&gt;    &lt;span class="rem"&gt;// Evito que la excepción siga subiendo y tumbe&lt;/span&gt;&lt;/pre&gt;&lt;pre class="alt"&gt;    &lt;span class="rem"&gt;// la aplicación marcándola como manejada:&lt;/span&gt;&lt;/pre&gt;&lt;pre&gt;    e.Handled = &lt;span class="kwrd"&gt;true&lt;/span&gt;;&lt;/pre&gt;&lt;pre class="alt"&gt;}&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Más info: &lt;a href="http://msdn2.microsoft.com/es-es/library/ms743714.aspx"&gt;Información general sobre la administración de aplicaciones&lt;/a&gt; (WPF).&lt;/p&gt;
&lt;h6&gt;&lt;a href="http://www.vtortola.net/post/Forzando-la-captura-de-excepciones-no-manejadas-en-WPF.aspx"&gt;Forzando la captura de excepciones no manejadas en WPF| vtortola.NET&lt;/a&gt;&lt;/h6&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://geeks.ms/aggbug.aspx?PostID=81335" width="1" height="1"&gt;</description><category domain="http://geeks.ms/blogs/vtortola/archive/tags/Excepciones/default.aspx">Excepciones</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/C_2300_+3.0/default.aspx">C# 3.0</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/WPF/default.aspx">WPF</category><category domain="http://geeks.ms/blogs/vtortola/archive/tags/.NET+3.5/default.aspx">.NET 3.5</category></item></channel></rss>

