<feed xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:trackback="http://madskills.com/public/xml/rss/module/trackback/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/" xmlns="http://www.w3.org/2005/Atom" xml:lang="en-US">
    <title>Greg Young</title>
    <link rel="self" type="application/xml" href="http://geekswithblogs.net/gyoung/Atom.aspx" />
    <subtitle type="html">Greg.ToString()</subtitle>
    <id>http://geekswithblogs.net/gyoung/Default.aspx</id>
    <author>
        <name>Greg Young</name>
        <uri>http://geekswithblogs.net/gyoung/Default.aspx</uri>
    </author>
    <generator uri="http://subtextproject.com" version="Subtext Version 0.0.0.0">Subtext</generator>
    <updated>2006-06-09T16:29:40Z</updated>
    <entry>
        <title>Blog moving</title>
        <link rel="self" type="text/html" href="http://geekswithblogs.net/gyoung/archive/2006/06/09/81349.aspx" />
        <id>http://geekswithblogs.net/gyoung/archive/2006/06/09/81349.aspx</id>
        <published>2006-06-09T16:30:00-05:00:00</published>
        <updated>2006-06-09T16:30:00Z</updated>
        <content type="html">&lt;P&gt;I have enjoyed my time here at geekswithblogs (even the green monster) but I will be moving my blog to codebetter.com. Topics the same, URL different.&lt;/P&gt;
&lt;P&gt;This blog will be moving to &lt;A href="http://codebetter.com/blogs/gregyoung"&gt;http://codebetter.com/blogs/gregyoung&lt;/A&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;&lt;img src="http://geekswithblogs.net/gyoung/aggbug/81349.aspx" width="1" height="1" /&gt;</content>
        <wfw:comment>http://geekswithblogs.net/gyoung/comments/81349.aspx</wfw:comment>
        <slash:comments>7</slash:comments>
        <wfw:commentRss>http://geekswithblogs.net/gyoung/comments/commentRss/81349.aspx</wfw:commentRss>
        <trackback:ping>http://geekswithblogs.net/gyoung/services/trackbacks/81349.aspx</trackback:ping>
    </entry>
    <entry>
        <title>C# FP Math Leaky Abstraction</title>
        <link rel="self" type="text/html" href="http://geekswithblogs.net/gyoung/archive/2006/06/05/80747.aspx" />
        <id>http://geekswithblogs.net/gyoung/archive/2006/06/05/80747.aspx</id>
        <published>2006-06-05T06:41:00-05:00:00</published>
        <updated>2006-06-06T15:44:00Z</updated>
        <content type="html">&lt;P&gt;Some you have probably seen a post from last Tuesday entitled &lt;A href="http://geekswithblogs.net/gyoung/archive/2006/05/30/80119.aspx"&gt;Floating Point Fun&lt;/A&gt;. If you have not read this I would recommend going back and reading it before continuing. In this post I discuss some of the interesting things that can happen when dealing with floating point math in C#, it is important to note that these items did not happen in version 1.x of the framework. &lt;/P&gt;
&lt;P&gt;The root of these problems is that when in a register the floating point is treated with a different precision than when it is being held in memory. As such you can run into cases where you are comparing a Float32 or a Float64 against an 80 bit register based float. These equality comparisons (or conversions to other types such as an integer) can obviously fail due to the difference in precision. &lt;/P&gt;
&lt;P&gt;After tracing through the generated assembly, I found a great reference on the subject at &lt;A href="http://blogs.msdn.com/davidnotario/archive/2005/08/08/449092.aspx"&gt;David Notario's Blog&lt;/A&gt;. David correctly points out that this is not a CLR/JIT issue, in fact changes like this were eluded to in the CLR spec (there is a quote from the ECMA spec on his blog) or here &lt;A href="http://dotnet.di.unipi.it/EcmaSpec/PartitionI/cont11.html"&gt;http://dotnet.di.unipi.it/EcmaSpec/PartitionI/cont11.html#_Toc527182172&lt;/A&gt; &lt;/P&gt;
&lt;P&gt;&lt;SPAN style="FONT-SIZE: 10px; FONT-FAMILY: Arial"&gt;&lt;/SPAN&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;There was some documentation on this breaking change in 2.0. Here is the listing from &lt;A href="http://msdn.microsoft.com/netframework/programming/breakingchanges/runtime/clr.aspx"&gt;the breaking changes documentation&lt;/A&gt; &lt;/P&gt;
&lt;P&gt;&lt;SPAN style="FONT-SIZE: 8px; COLOR: black; FONT-FAMILY: Verdana"&gt;&lt;FONT size=2&gt;In the CLR model, we assert that arguments, locals, and return values (things which you can't tell their size) can be expanded at will. When you say float, it means anything greater than or equal to a float. So we can sometimes give you what you asked for 'or better'. When we do this, we can spill 'extra' data, almost like a 'you only asked for 15 precision points, but congratulations! We gave you 18!'. If someone expected the floating point precision to always remain the exactly the same, they could be affected. In order to faciliate performance improvements and better scenarios, the CLR may rewrite (as in this case) parts of the register. For example, things that used to truncate because of spilling, no longer do. We make these kinds of changes all the time. We believe this is an appropriate change, and it is even called out specifically in the CLI specification, as something which can, and will occur with different iterations:&lt;/FONT&gt; &lt;/SPAN&gt;&lt;/P&gt;
&lt;P&gt;What makes these changes particularly nasty is that you are forced to second guess how the JIT works in order to provide consistent results. In my previous post I used the example of &lt;/P&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;&lt;SPAN style="FONT-FAMILY: Courier New"&gt;&lt;SPAN style="COLOR: blue"&gt;float&lt;/SPAN&gt; f = 97.09f; &lt;BR&gt;&lt;/SPAN&gt;&lt;SPAN style="FONT-FAMILY: Courier New"&gt;f = (f * 100f); &lt;BR&gt;&lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt; tmp = (&lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;)f; &lt;BR&gt;&lt;SPAN style="COLOR: teal"&gt;Console&lt;/SPAN&gt;.WriteLine(tmp);&lt;SPAN style="FONT-SIZE: 7px"&gt; &lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/P&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;This code will work in either debug or release mode when a debugger is attached, having the debugger attached will disable the JIT optimizations that cause the problem. It does as I describe in the previous post fail when run without the debugger. If we wanted it to work all of the time we would need to write it in the form. &lt;/P&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;&lt;SPAN style="FONT-SIZE: 10px; FONT-FAMILY: Courier New"&gt;
&lt;P&gt;&lt;FONT size=3&gt;&lt;SPAN style="COLOR: blue"&gt;float&lt;/SPAN&gt; f = 97.09f; &lt;BR&gt;f = (&lt;SPAN style="COLOR: blue"&gt;float&lt;/SPAN&gt;)(f * 100f); &lt;BR&gt;&lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt; tmp = (&lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;)f; &lt;BR&gt;&lt;SPAN style="COLOR: teal"&gt;Console&lt;/SPAN&gt;.WriteLine(tmp);&lt;/FONT&gt;&lt;/P&gt;&lt;/SPAN&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;The explicit cast to a float forces it to be narrowed back to a float32, without the narrowing it will actually be in a register as an 80 bit float. As such we end with a predictable behavior of always producing the correct result of 9709. &lt;/P&gt;
&lt;P&gt;The problem I have with this behavior is that it is a leaky abstraction. In order to have our code work properly (and to be efficient) we need to know exactly how the compiler and the JIT intends to optimize our code. This introduces a logical problem though as by its very definition we do not know how the JIT will optimize our code. The JIT very well could place this into a register at some times and not at others or the JIT run on a different platform could offer a different behavior than the JIT we tested with. &lt;/P&gt;
&lt;P&gt;This becomes especially nasty when dealing constants, consider the following code. &lt;/P&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;&lt;SPAN style="FONT-SIZE: 10px; FONT-FAMILY: Courier New"&gt;
&lt;P&gt;&lt;FONT size=3&gt;&lt;SPAN style="COLOR: blue"&gt;float&lt;/SPAN&gt; f = 97.09f; &lt;BR&gt;f = (f * 100f); &lt;BR&gt;&lt;SPAN style="COLOR: blue"&gt;bool&lt;/SPAN&gt; test = f == 97.09f * 100f; &lt;BR&gt;&lt;SPAN style="COLOR: teal"&gt;Console&lt;/SPAN&gt;.WriteLine(test);&lt;/FONT&gt;&lt;/P&gt;&lt;/SPAN&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;What is the value of test? The abstraction leaks for both the compiler and the JIT. To start with, are the floats actually being calculated at runtime or is the compiler smart enough to realize that they are constants? In this particular case the C# compiler generates instructions for the first floating point operation but recognizes that the second is a constant value and as such pre-computes the value. These types of scenarios are exactly the type of thing that compilers look for&amp;nbsp;when optimizing.&amp;nbsp;&lt;/P&gt;
&lt;P&gt;If the compiler did &lt;STRONG&gt;not&lt;/STRONG&gt; recognize the constant expression this might work as both of the calculations would have been done with their result being saved in a register, at that point we would actually have to look at how the JIT handled this case. Both of these items may change based upon environment. &lt;/P&gt;
&lt;P&gt;The CLR has basically left the choice to the language as to how it wants to handle these cases. Visual C++ has handled this by providing &lt;A href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dv_vstechart/html/floapoint.asp"&gt;compiler switches&lt;/A&gt;. The link is also interesting as it deals with how the switches apply as well to optimizations that occur within the compiler that can cause further issues. C# does not have many such optimizations at this point but it is only a matter of time before they get introduced. &lt;/P&gt;
&lt;P&gt;&lt;STRONG&gt;I would therefore propose that C# should be given switches as well (similar to those available for C++) which could allow for the automatic narrowing of floating point values. &lt;/STRONG&gt;&lt;/P&gt;
&lt;P&gt;It is often brought up that C# does it the way it does it for performance reasons; it is obviously faster to leave values in registers when possible as opposed to narrowing them. The only way consistent way of doing it is through the use of the narrowing. From all of the studies I have seen, C# is primarily used for business applications where consistency (and reduction of programmer thought) is the primary goal and quite often run-time speed is sacrificed in order to better meet these goals (think abstractions). If an argument can be made for C++ to have an option of a precise switch, I would imagine a better argument can in fact be made for C#.&lt;/P&gt;
&lt;P&gt;&lt;STRONG&gt;Based upon this I would also propose that the default behavior of the compiler should be to support consistent operations (/fp:precise in C++). &lt;/STRONG&gt;&lt;/P&gt;
&lt;P&gt;This switch would not eliminate people from writing code that was dependent upon how the compiler/JIT treated things; it would however force the programmer to make a conscious decision by setting the switch that they were assuming the risks associated with the performance gains. VC++ by default runs with /fp:precise so I would not think it a large jump to make the C# compiler consistent. &lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;As a note for the people I am sure will say, &amp;#8220;don't do this .. use a precision range or round instead&amp;#8220;. These are simply examples ... I am fine with using these solutions (in fact I normally use range checks). The problem is that code like this crops up regularly and it creates a very subtle problem (that did not exist in 1.x). That and there are times when you actually want (validly) to do an equivalence test on two floating point numbers that should have a consistent value (i.e. results of the same calculation). &lt;STRONG&gt;If these operations are to be disallowed, that is fine as well .. but lets completely disallow them and have the compiler generate an warning/error in the circumstance.&lt;/STRONG&gt;&lt;/P&gt;
&lt;P&gt;This issue is known by very few, if you agree with the concepts here I ask you to either leave a comment below or to link to the post on your blog. Hopefully getting this knowledge more into the mainstream will both reduce the number of bugs caused by this subtlety and bring more focus on it by those with the power to change it.&lt;/P&gt;&lt;img src="http://geekswithblogs.net/gyoung/aggbug/80747.aspx" width="1" height="1" /&gt;</content>
        <wfw:comment>http://geekswithblogs.net/gyoung/comments/80747.aspx</wfw:comment>
        <slash:comments>8</slash:comments>
        <wfw:commentRss>http://geekswithblogs.net/gyoung/comments/commentRss/80747.aspx</wfw:commentRss>
        <trackback:ping>http://geekswithblogs.net/gyoung/services/trackbacks/80747.aspx</trackback:ping>
    </entry>
    <entry>
        <title>GetGenericArguments</title>
        <link rel="self" type="text/html" href="http://geekswithblogs.net/gyoung/archive/2006/05/28/79857.aspx" />
        <id>http://geekswithblogs.net/gyoung/archive/2006/05/28/79857.aspx</id>
        <published>2006-05-28T05:24:00-05:00:00</published>
        <updated>2006-06-05T04:10:00Z</updated>
        <content type="html">&lt;P&gt;I have been searching for an answer to this one and I am perplexed.&lt;/P&gt;
&lt;P&gt;&lt;A href="http://msdn2.microsoft.com/en-us/library/system.type.getgenericarguments.aspx"&gt;http://msdn2.microsoft.com/en-us/library/system.type.getgenericarguments.aspx&lt;/A&gt;&amp;nbsp;returns an array of the generic arguments .. what I can't figure out is if they will ever be out of order. The arguments themselves have a position on them, is it possible that I get them back out of order where I would need to re-order them ...&lt;/P&gt;
&lt;P&gt;basically what I am doing is something similar to the following on a generic type definition&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; string [] Params = new string[typeArguments.Length];&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; for (int i=0;i&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Params[i] = typeArguments[i].Name;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; GenericTypeParameterBuilder[] typeParams = outputType.DefineGenericParameters(Params);&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Debug.Assert(typeParams.Length == typeArguments.Length);&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; for(int i=0;i&lt;TYPEPARAMS.LENGTH;I++) {&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; GenericTypeParameterBuilder builder = typeParams[i];&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Type OriginalType = typeArguments[i];&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; builder.SetGenericParameterAttributes(OriginalType.GenericParameterAttributes);&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; builder.SetInterfaceConstraints(OriginalType.GetGenericParameterConstraints());&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;I have to say as well that&amp;nbsp;I am rather unimpressed with the bridge I am forced to put up here .. it would be alot nicer to just pass through the generic arguments I already have as opposed to creating a string [] then iterating through .. maybe I am missing something with the API?&lt;/P&gt;
&lt;P&gt;and for those who know me well .. you probably know what I am working on .. (hint, the topic this is posted in)\&lt;/P&gt;
&lt;P&gt;&lt;FONT color=#ff0000&gt;Update: it seems the documentation has been updated to reflect the return being sorted &lt;A href="http://msdn2.microsoft.com/en-us/library/system.type.getgenericarguments.aspx"&gt;http://msdn2.microsoft.com/en-us/library/system.type.getgenericarguments.aspx&lt;/A&gt;&lt;/FONT&gt;&lt;/P&gt;&lt;img src="http://geekswithblogs.net/gyoung/aggbug/79857.aspx" width="1" height="1" /&gt;</content>
        <wfw:comment>http://geekswithblogs.net/gyoung/comments/79857.aspx</wfw:comment>
        <slash:comments>2</slash:comments>
        <wfw:commentRss>http://geekswithblogs.net/gyoung/comments/commentRss/79857.aspx</wfw:commentRss>
        <trackback:ping>http://geekswithblogs.net/gyoung/services/trackbacks/79857.aspx</trackback:ping>
    </entry>
    <entry>
        <title>Fireworks to XAML converter</title>
        <link rel="self" type="text/html" href="http://geekswithblogs.net/gyoung/archive/2006/06/03/80604.aspx" />
        <id>http://geekswithblogs.net/gyoung/archive/2006/06/03/80604.aspx</id>
        <published>2006-06-03T00:32:00-05:00:00</published>
        <updated>2006-06-03T00:32:00Z</updated>
        <content type="html">&lt;P&gt;slick! &lt;A href="http://www.granthinkson.com/?p=35"&gt;http://www.granthinkson.com/?p=35&lt;/A&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;This is looking useful!&lt;/P&gt;&lt;img src="http://geekswithblogs.net/gyoung/aggbug/80604.aspx" width="1" height="1" /&gt;</content>
        <wfw:comment>http://geekswithblogs.net/gyoung/comments/80604.aspx</wfw:comment>
        <slash:comments>2</slash:comments>
        <wfw:commentRss>http://geekswithblogs.net/gyoung/comments/commentRss/80604.aspx</wfw:commentRss>
        <trackback:ping>http://geekswithblogs.net/gyoung/services/trackbacks/80604.aspx</trackback:ping>
    </entry>
    <entry>
        <title>Private Object Namespaces and Condition Variables </title>
        <link rel="self" type="text/html" href="http://geekswithblogs.net/gyoung/archive/2006/06/01/80392.aspx" />
        <id>http://geekswithblogs.net/gyoung/archive/2006/06/01/80392.aspx</id>
        <published>2006-06-01T19:04:00-05:00:00</published>
        <updated>2006-06-01T19:21:00Z</updated>
        <content type="html">&lt;P&gt;I knew there was a reason I kept &lt;A href="http://blogs.msdn.com/junfeng/default.aspx"&gt;Junfeng Zhang's Blog&lt;/A&gt; on my list (even during the slow months). I hadn&amp;#8217;t checked the blog in a few weeks but reading it now just made my &lt;STRONG&gt;day&lt;/STRONG&gt;. &lt;/P&gt;
&lt;P&gt;There are two new items listed on the blog. The first is that someone fixed a huge security hole, I have actually run into this particular security hole. Junfeng calls it &lt;EM&gt;kernel object name squatting&lt;/EM&gt;. I have never heard it called by this name but it is a pretty simple problem. Shared objects between process are shared the question is who protects them from prying eyes? &lt;/P&gt;
&lt;P&gt;Let&amp;#8217;s propose you have the following code (note this is a trivial example and likely has bugs in it but it should illustrate the point). &lt;/P&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;&lt;SPAN style="FONT-SIZE: 10px; FONT-FAMILY: Courier New"&gt;
&lt;P&gt;&lt;FONT size=3&gt;&lt;SPAN style="COLOR: blue"&gt;static&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;void&lt;/SPAN&gt; Main(&lt;SPAN style="COLOR: blue"&gt;string&lt;/SPAN&gt;[] args) { &lt;BR&gt;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;bool&lt;/SPAN&gt; Created; &lt;BR&gt;&amp;nbsp; &lt;SPAN style="COLOR: teal"&gt;Mutex&lt;/SPAN&gt; m = &lt;SPAN style="COLOR: blue"&gt;new&lt;/SPAN&gt; &lt;SPAN style="COLOR: teal"&gt;Mutex&lt;/SPAN&gt;(&lt;SPAN style="COLOR: blue"&gt;false&lt;/SPAN&gt;, &lt;SPAN style="COLOR: maroon"&gt;"MutexWeWillSteal2"&lt;/SPAN&gt;, &lt;SPAN style="COLOR: blue"&gt;out&lt;/SPAN&gt; Created); &lt;BR&gt;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;if&lt;/SPAN&gt; (Created) { &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: teal"&gt;Console&lt;/SPAN&gt;.WriteLine(&lt;SPAN style="COLOR: maroon"&gt;"MutexCreated"&lt;/SPAN&gt;); &lt;BR&gt;&amp;nbsp; } &lt;BR&gt;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;for&lt;/SPAN&gt; (&lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt; i = 0; i &amp;lt; 100; i++) { &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: teal"&gt;Thread&lt;/SPAN&gt;.Sleep(200); &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;bool&lt;/SPAN&gt; havelock = &lt;SPAN style="COLOR: blue"&gt;false&lt;/SPAN&gt;; &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;try &lt;/SPAN&gt;{&amp;nbsp;&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;havelock = m.WaitOne(5000, &lt;SPAN style="COLOR: blue"&gt;false&lt;/SPAN&gt;); &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;if&lt;/SPAN&gt; (havelock) { &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: teal"&gt;Console&lt;/SPAN&gt;.WriteLine(&lt;SPAN style="COLOR: maroon"&gt;"acquired lock"&lt;/SPAN&gt;); &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: teal"&gt;Thread&lt;/SPAN&gt;.Sleep(500);&amp;nbsp;&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;} &lt;SPAN style="COLOR: blue"&gt;else &lt;/SPAN&gt;{ &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: teal"&gt;Console&lt;/SPAN&gt;.WriteLine(&lt;SPAN style="COLOR: maroon"&gt;"Unable to acquire lock"&lt;/SPAN&gt;); &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; } &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; } &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;finally&lt;/SPAN&gt; { &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;if&lt;/SPAN&gt; (havelock)&amp;nbsp;{ &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; m.ReleaseMutex();&amp;nbsp;&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&amp;nbsp;&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;BR&gt;&amp;nbsp;&amp;nbsp;} &lt;BR&gt;}&lt;/FONT&gt;&lt;/P&gt;&lt;/SPAN&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;As we can see this application is simply starting up, creating a mutex if it does not exist already then simply obtaining and releasing the lock. You can quite easily bring up two of these applications to notice that they are synchronizing with each other. Using a named mutex like this is extremely common in order to synchronize two processes. &lt;/P&gt;
&lt;P&gt;The problem with mutex is not as great as some objects as I can apply an ACL to prevent people not at a certain level from accessing it. Unfortunately I still suffer from a denial of service attack from applications at my own level. One can quite easily use the debugger (or other tools) to find out the names of the objects I am using (!handle in windbg will bring this right up for me). Once I have that name I can write a bit of code such as the following. &lt;/P&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;&lt;SPAN style="FONT-SIZE: 10px; FONT-FAMILY: Courier New"&gt;
&lt;P&gt;&lt;FONT size=3&gt;&lt;SPAN style="COLOR: blue"&gt;static&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;void&lt;/SPAN&gt; Main(&lt;SPAN style="COLOR: blue"&gt;string&lt;/SPAN&gt;[] args) &lt;/FONT&gt;&lt;/P&gt;
&lt;P&gt;&lt;FONT size=3&gt;{ &lt;BR&gt;&lt;SPAN style="COLOR: blue"&gt;bool&lt;/SPAN&gt; Created; &lt;BR&gt;&lt;SPAN style="COLOR: teal"&gt;Mutex&lt;/SPAN&gt; m = &lt;SPAN style="COLOR: blue"&gt;new&lt;/SPAN&gt; &lt;SPAN style="COLOR: teal"&gt;Mutex&lt;/SPAN&gt;(&lt;SPAN style="COLOR: blue"&gt;true&lt;/SPAN&gt;, &lt;SPAN style="COLOR: maroon"&gt;"MutexWeWillSteal2"&lt;/SPAN&gt;, &lt;SPAN style="COLOR: blue"&gt;out&lt;/SPAN&gt; Created); &lt;BR&gt;m.WaitOne(-1, &lt;SPAN style="COLOR: blue"&gt;false&lt;/SPAN&gt;); &lt;BR&gt;&lt;SPAN style="COLOR: teal"&gt;Thread&lt;/SPAN&gt;.Sleep(&lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;.MaxValue); &lt;BR&gt;}&lt;/FONT&gt;&lt;/P&gt;&lt;/SPAN&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;Providing this code access the mutex before our other processes, our other processes will just fail. We have effectively made the other application unable to do anything (the basis of a denial of service attack). &lt;/P&gt;
&lt;P&gt;What is being introduced in LH is the ability for me to make my two processes share a namespace. As such their namespace can be protected. The malicious program can start but one can avoid it from having access to the mutex &lt;A href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dllproc/base/object_namespaces.asp"&gt;http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dllproc/base/object_namespaces.asp&lt;/A&gt; explains exactly how it works but basically the processes that want to share the data define a boundary (and requirements to get into the boundary that they both share)&lt;EM&gt; &lt;/EM&gt;&lt;/P&gt;
&lt;P&gt;&lt;EM&gt;&lt;FONT size=3&gt;&lt;SPAN style="FONT-SIZE: 8px; FONT-FAMILY: Verdana"&gt;&lt;FONT size=2&gt;This function requires that you specify a boundary that defines how the objects in the namespace are to be isolated. Boundaries can include security identifiers (SID), session numbers, or any type of information defined by the application. The caller must be within the specified boundary for the create operation to succeed.&lt;/FONT&gt;&lt;/SPAN&gt; &lt;/FONT&gt;&lt;/EM&gt;&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;The second post I found really interesting was condition variables &lt;A href="http://msdn.microsoft.com/library/en-us/dllproc/base/using_condition_variables.asp"&gt;http://msdn.microsoft.com/library/en-us/dllproc/base/using_condition_variables.asp&lt;/A&gt;. Condition Variables are one of the 3 locking mechanisms (along with mutex and semaphore). I do not quite understand the excitement over it (perhaps POSIX compatibility?). I was under the possibly misinformed impression that it was roughly equivalent to Events in windows. &lt;/P&gt;
&lt;P&gt;Basically I can in POSIX use &lt;/P&gt;
&lt;P&gt;Pthread_signal() which alerts one thread waitingPthread_boradcast() which alerts all of my threads waiting &lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;In Win32 I can use &lt;/P&gt;
&lt;P&gt;PulseEvent() but there are two types of events &lt;/P&gt;
&lt;P&gt;AutoResetEvent which will only let one thread though and ManualResetEvent which I can use to let some or all through &lt;/P&gt;
&lt;P&gt;I am now morbidly curious on the subject; it has been way too long since I was at this level &lt;/P&gt;&lt;img src="http://geekswithblogs.net/gyoung/aggbug/80392.aspx" width="1" height="1" /&gt;</content>
        <wfw:comment>http://geekswithblogs.net/gyoung/comments/80392.aspx</wfw:comment>
        <slash:comments>2</slash:comments>
        <wfw:commentRss>http://geekswithblogs.net/gyoung/comments/commentRss/80392.aspx</wfw:commentRss>
        <trackback:ping>http://geekswithblogs.net/gyoung/services/trackbacks/80392.aspx</trackback:ping>
    </entry>
    <entry>
        <title>Unit Test???</title>
        <link rel="self" type="text/html" href="http://geekswithblogs.net/gyoung/archive/2006/05/31/80292.aspx" />
        <id>http://geekswithblogs.net/gyoung/archive/2006/05/31/80292.aspx</id>
        <published>2006-05-31T21:23:00-05:00:00</published>
        <updated>2006-05-31T22:00:00Z</updated>
        <content type="html">&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;FONT face=Arial color=#000000&gt;I was poking through &lt;/FONT&gt;&lt;A href="http://jasonhaley.com/blog/default.aspx"&gt;&lt;FONT face=Arial color=#000000&gt;Jason Haley's&lt;/FONT&gt;&lt;/A&gt;&lt;FONT face=Arial color=#000000&gt; blog today when I came across one of his interesting links (which are usually pretty interesting btw). It pointed to a post by &lt;/FONT&gt;&lt;A href="http://haacked.com/"&gt;&lt;FONT face=Arial color=#000000&gt;Phillip Haack&lt;/FONT&gt;&lt;/A&gt;&lt;FONT face=Arial color=#000000&gt; titled &lt;/FONT&gt;&lt;A href="http://haacked.com/archive/2006/05/30/ATestingMailServerForUnitTestingEmailFunctionality.aspx"&gt;&lt;FONT face=Arial color=#000000&gt;A Testing Mail Server for Unit Testing Email Functionality&lt;/FONT&gt;&lt;/A&gt;&lt;FONT face=Arial color=#000000&gt;. I generally enjoy reading about other&amp;#8217;s unit testing experiences as I often gain quite a bit of perspective (and get to see a lot of problems I may not otherwise get to see).&lt;/FONT&gt;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;Basically what he has done is taken an open source SMTP server and used it for in order to allow his unit tests to check to see if an email that was sent through the .NET email libraries actually arrived at its sender. &lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;Let me say that he has come up with a very inventive way of automating this integration test. I personally think that his code is extremely useful for automated integration testing. I have to admit, I have done automated integration tests for emailing and I used a far less elegant solution.&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;?xml:namespace prefix = o ns = "urn:schemas-microsoft-com:office:office" /&gt;&lt;o:p&gt;&lt;FONT face=Arial color=#000000&gt;&amp;nbsp;&lt;/FONT&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;As I was reading through the post I came across the comment.&lt;I style="mso-bidi-font-style: normal"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/I&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;I style="mso-bidi-font-style: normal"&gt;&lt;SPAN lang=EN style="COLOR: #222222; FONT-FAMILY: 'Verdana','sans-serif'; mso-ansi-language: EN"&gt;&lt;FONT face=Arial color=#000000&gt;As for the semantic arguments around whether this really constitutes an &lt;SPAN style="mso-bidi-font-style: italic"&gt;Integration Test&lt;/SPAN&gt; as opposed to a &lt;SPAN style="mso-bidi-font-style: italic"&gt;Unit Test&lt;/SPAN&gt;, please don&amp;#8217;t bore me with your hang-ups. Either way, it deserves a test and what better way to test it than using something like &lt;/FONT&gt;&lt;A title="MbUnit Generative Unit Testing Framework (new window)" href="http://www.mertner.com/confluence/display/MbUnit/Home" target=_blank&gt;&lt;SPAN style="COLOR: #226699"&gt;&lt;FONT face=Arial color=#000000&gt;MbUnit&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/A&gt;&lt;FONT face=Arial color=#000000&gt; or &lt;/FONT&gt;&lt;A title="NUnit Unit Testing Framework (new window)" href="http://nunit.com/" target=_blank&gt;&lt;SPAN style="COLOR: #226699"&gt;&lt;FONT face=Arial color=#000000&gt;NUnit&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/A&gt;&lt;FONT face=Arial color=#000000&gt;.&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/I&gt;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;I style="mso-bidi-font-style: normal"&gt;&lt;SPAN lang=EN style="COLOR: #222222; FONT-FAMILY: 'Verdana','sans-serif'; mso-ansi-language: EN"&gt;&lt;FONT face=Arial color=#000000&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/I&gt;&amp;nbsp;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;Well, let me start by saying it is an integration test at best (I might even classify this as a user acceptance type test) and has no place being a unit test. &lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp;&lt;/SPAN&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;He did however hit the appropriate unit test on the head earlier in his post when he suggested an EmailProvider (I say EmailService but that truly is semantics) which could then be mocked for testing purposes. I would personally either create my own abstraction of an &amp;#8220;Email&amp;#8221; class or use the one from System.Net.Mail as a parameter instead of passing parameters but the reasons for this will have to wait for another post.&lt;o:p&gt;&lt;/o:p&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;o:p&gt;&lt;FONT face=Arial color=#000000&gt;&amp;nbsp;&lt;/FONT&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;That said let&amp;#8217;s look at the test case he created to test that email actually got delivered.&lt;o:p&gt;&lt;/o:p&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/P&gt;
&lt;TABLE class=MsoTableGrid style="BORDER-RIGHT: medium none; BORDER-TOP: medium none; BORDER-LEFT: medium none; BORDER-BOTTOM: medium none; BORDER-COLLAPSE: collapse; mso-border-alt: solid black .5pt; mso-padding-alt: 0in 5.4pt 0in 5.4pt; mso-border-themecolor: text1; mso-yfti-tbllook: 1184" cellSpacing=0 cellPadding=0 border=1&gt;
&lt;TBODY&gt;
&lt;TR style="mso-yfti-irow: 0; mso-yfti-firstrow: yes; mso-yfti-lastrow: yes"&gt;
&lt;TD style="BORDER-RIGHT: black 1pt solid; PADDING-RIGHT: 5.4pt; BORDER-TOP: black 1pt solid; PADDING-LEFT: 5.4pt; PADDING-BOTTOM: 0in; BORDER-LEFT: black 1pt solid; WIDTH: 7.65in; PADDING-TOP: 0in; BORDER-BOTTOM: black 1pt solid; BACKGROUND-COLOR: transparent; mso-border-alt: solid black .5pt; mso-border-themecolor: text1" vAlign=top width=734&gt;&lt;PRE style="BACKGROUND: white; LINE-HEIGHT: 19.2pt"&gt;&lt;FONT size=2&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;DotNetOpenMailProvider provider = &lt;/SPAN&gt;&lt;SPAN class=kwrd1&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;new&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;FONT face=Arial color=#000000&gt; DotNetOpenMailProvider();&lt;BR&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;FONT size=2&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;NameValueCollection configValue = &lt;/SPAN&gt;&lt;SPAN class=kwrd1&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;new&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;FONT face=Arial color=#000000&gt; NameValueCollection();&lt;BR&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;FONT size=2&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;configValue[&lt;/SPAN&gt;&lt;SPAN class=str1&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;"smtpServer"&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;] = &lt;/SPAN&gt;&lt;SPAN class=str1&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;"127.0.0.1"&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;FONT face=Arial color=#000000&gt;;&lt;BR&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;FONT size=2&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;configValue[&lt;/SPAN&gt;&lt;SPAN class=str1&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;"port"&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;] = &lt;/SPAN&gt;&lt;SPAN class=str1&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;"8081"&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;;&lt;o:p&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/PRE&gt;&lt;PRE style="BACKGROUND: white; LINE-HEIGHT: 19.2pt"&gt;&lt;FONT size=2&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;provider.Initialize(&lt;/SPAN&gt;&lt;SPAN class=str1&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;"providerTest"&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;, configValue);&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;o:p&gt;&lt;FONT size=2&gt;&lt;BR&gt;&lt;/FONT&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;FONT size=2&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;TestSmtpServer receivingServer = &lt;/SPAN&gt;&lt;SPAN class=kwrd1&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;new&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;FONT face=Arial color=#000000&gt; TestSmtpServer();&lt;BR&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;FONT size=2&gt;&lt;FONT face=Arial color=#000000&gt;&lt;SPAN class=kwrd1&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;try&lt;BR&gt;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;FONT face=Arial color=#000000 size=2&gt;{&lt;BR&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;FONT size=2&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;/SPAN&gt;receivingServer.Start(&lt;/SPAN&gt;&lt;SPAN class=str1&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;"127.0.0.1"&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;FONT face=Arial color=#000000&gt;, 8081);&lt;BR&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;FONT size=2&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;/SPAN&gt;provider.Send(&lt;/SPAN&gt;&lt;SPAN class=str1&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;A href="mailto:phil@example.com"&gt;phil@example.com&lt;/A&gt;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;FONT face=Arial color=#000000&gt;, &lt;BR&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;FONT size=2&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN class=str1&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;A href="mailto:nobody@example.com"&gt;nobody@example.com&lt;/A&gt;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;FONT face=Arial color=#000000&gt;, &lt;BR&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;FONT size=2&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN class=str1&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;"Subject to nothing"&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;FONT face=Arial color=#000000&gt;, &lt;BR&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;FONT size=2&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN class=str1&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;"Mr. Watson. Come here. I need you."&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;);&lt;o:p&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/PRE&gt;&lt;PRE style="BACKGROUND: white; LINE-HEIGHT: 19.2pt"&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;FONT face=Arial color=#000000 size=2&gt;}&lt;BR&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;FONT size=2&gt;&lt;FONT face=Arial color=#000000&gt;&lt;SPAN class=kwrd1&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;finally&lt;BR&gt;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;FONT face=Arial color=#000000 size=2&gt;{&lt;BR&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;FONT size=2&gt;&lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;/SPAN&gt;receivingServer.Stop();&lt;BR&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;FONT size=2&gt;}&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;o:p&gt;&lt;FONT size=2&gt;&lt;BR&gt;&lt;/FONT&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;FONT size=2&gt;&lt;FONT face=Arial color=#000000&gt;&lt;SPAN class=rem1&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;// So Did It Work?&lt;BR&gt;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;FONT face=Arial color=#000000 size=2&gt;Assert.AreEqual(1, receivingServer.Inbox.Count);&lt;BR&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;&lt;FONT size=2&gt;ReceivedEmailMessage received = receivingServer.Inbox[0];&lt;BR&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;FONT size=2&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;Assert.AreEqual(&lt;/SPAN&gt;&lt;SPAN class=str1&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;"phil@example.com"&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;, received.ToAddress.Email);&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/PRE&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;B style="mso-bidi-font-weight: normal"&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;o:p&gt;&lt;FONT face=Arial color=#000000&gt;&amp;nbsp;&lt;/FONT&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/B&gt;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;I can identify a few places that could cause this test to fail that would not cause our mock to fail otherwise.&lt;o:p&gt;&lt;/o:p&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/P&gt;
&lt;P class=MsoListParagraphCxSpFirst style="MARGIN: 0in 0in 0pt 0.5in; TEXT-INDENT: -0.25in; mso-list: l0 level1 lfo1"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN; mso-bidi-font-family: Calibri; mso-bidi-theme-font: minor-latin"&gt;&lt;SPAN style="mso-list: Ignore"&gt;1)&lt;SPAN style="FONT: 7pt 'Times New Roman'"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;We did not properly setup our &lt;SPAN style="COLOR: black"&gt;configValue[&lt;/SPAN&gt;&lt;SPAN class=str1&gt;"smtpServer"&lt;/SPAN&gt;&lt;SPAN style="COLOR: black"&gt;] configuration&lt;/SPAN&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/P&gt;
&lt;P class=MsoListParagraphCxSpMiddle style="MARGIN: 0in 0in 0pt 0.5in; TEXT-INDENT: -0.25in; mso-list: l0 level1 lfo1"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN; mso-bidi-font-family: Calibri; mso-bidi-theme-font: minor-latin"&gt;&lt;SPAN style="mso-list: Ignore"&gt;2)&lt;SPAN style="FONT: 7pt 'Times New Roman'"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;We did not properly setup our configValue[&lt;/SPAN&gt;&lt;SPAN class=str1&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;"port"&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;] configuration&lt;/SPAN&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/P&gt;
&lt;P class=MsoListParagraphCxSpMiddle style="MARGIN: 0in 0in 0pt 0.5in; TEXT-INDENT: -0.25in; mso-list: l0 level1 lfo1"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN; mso-bidi-font-family: Calibri; mso-bidi-theme-font: minor-latin"&gt;&lt;SPAN style="mso-list: Ignore"&gt;3)&lt;SPAN style="FONT: 7pt 'Times New Roman'"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;Someone is already listening on our configured port&lt;/SPAN&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/P&gt;
&lt;P class=MsoListParagraphCxSpMiddle style="MARGIN: 0in 0in 0pt 0.5in; TEXT-INDENT: -0.25in; mso-list: l0 level1 lfo1"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN; mso-bidi-font-family: Calibri; mso-bidi-theme-font: minor-latin"&gt;&lt;SPAN style="mso-list: Ignore"&gt;4)&lt;SPAN style="FONT: 7pt 'Times New Roman'"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;We did not properly start our testing server &lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp;&lt;/SPAN&gt;or it is failing in some way (i.e. configuration)&lt;/SPAN&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/P&gt;
&lt;P class=MsoListParagraphCxSpMiddle style="MARGIN: 0in 0in 0pt 0.5in; TEXT-INDENT: -0.25in; mso-list: l0 level1 lfo1"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN; mso-bidi-font-family: Calibri; mso-bidi-theme-font: minor-latin"&gt;&lt;SPAN style="mso-list: Ignore"&gt;5)&lt;SPAN style="FONT: 7pt 'Times New Roman'"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;We have a firewall that prevents the communication from working between the client and our email server&lt;/SPAN&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/P&gt;
&lt;P class=MsoListParagraphCxSpMiddle style="MARGIN: 0in 0in 0pt 0.5in; TEXT-INDENT: -0.25in; mso-list: l0 level1 lfo1"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN; mso-bidi-font-family: Calibri; mso-bidi-theme-font: minor-latin"&gt;&lt;SPAN style="mso-list: Ignore"&gt;6)&lt;SPAN style="FONT: 7pt 'Times New Roman'"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;There is no accessible network between the client and the server&lt;/SPAN&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/P&gt;
&lt;P class=MsoListParagraphCxSpMiddle style="MARGIN: 0in 0in 0pt 0.5in; TEXT-INDENT: -0.25in; mso-list: l0 level1 lfo1"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN; mso-bidi-font-family: Calibri; mso-bidi-theme-font: minor-latin"&gt;&lt;SPAN style="mso-list: Ignore"&gt;7)&lt;SPAN style="FONT: 7pt 'Times New Roman'"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;The Ethernet elves ate the address that the mail was sent to&lt;/SPAN&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/P&gt;
&lt;P class=MsoListParagraphCxSpLast style="MARGIN: 0in 0in 10pt 0.5in; TEXT-INDENT: -0.25in; mso-list: l0 level1 lfo1"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN; mso-bidi-font-family: Calibri; mso-bidi-theme-font: minor-latin"&gt;&lt;SPAN style="mso-list: Ignore"&gt;8)&lt;SPAN style="FONT: 7pt 'Times New Roman'"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="COLOR: black; mso-ansi-language: EN"&gt;Numerous other environmental factors&lt;/SPAN&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;Are you noticing a pattern in these items? We could have configuration failures, failures in our test code, or environmental failures; not a single case is actually testing &lt;STRONG&gt;our &lt;/STRONG&gt;code beyond what a mock would do. When our test fails it only tells us that the environment that the test was run in was not appropriate for the test code and as such the test failed. I thought that unit tests were supposed to test your code?&lt;o:p&gt;&lt;/o:p&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;B style="mso-bidi-font-weight: normal"&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;The test results are not dependent upon the code in question; they are dependent upon the testing environment. &lt;o:p&gt;&lt;/o:p&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/B&gt;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;If we were to try to come up with an analogy for the type of unit test this was we could say it is like testing your car by turning it on. When the car turns on we can have a grand celebration that our car did in fact turn on, but what if the car does &lt;B style="mso-bidi-font-weight: normal"&gt;not &lt;/B&gt;turn on. All we have gained from this test is that the car did not turn on; we have no insight as to &lt;B style="mso-bidi-font-weight: normal"&gt;why&lt;/B&gt; the car did not turn on. &lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp;&lt;/SPAN&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;B style="mso-bidi-font-weight: normal"&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;Any time we have a unit test which gives us no insight as to why a failure is occurring we need to re-think the value of the unit test.&lt;o:p&gt;&lt;/o:p&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/B&gt;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;What if the test succeeds, does that tell us our code works? &lt;B style="mso-bidi-font-weight: normal"&gt;No&lt;/B&gt; it tells us that the email client we used was compatible with our test email server and that our testing environment was setup appropriately to run the test.&lt;o:p&gt;&lt;/o:p&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;o:p&gt;&lt;FONT face=Arial color=#000000&gt;&amp;nbsp;&lt;/FONT&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;Unit tests are overhead for a system. They are no different than documentation; they need to pull their weight in order to stay around. Let me go back to the quote statement saying that this does not actually deserve a test. This particular test carries with it a lot of baggage, &lt;o:p&gt;&lt;/o:p&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/P&gt;
&lt;P class=MsoListParagraphCxSpFirst style="MARGIN: 0in 0in 0pt 0.5in; TEXT-INDENT: -0.25in; mso-list: l1 level1 lfo2"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN; mso-bidi-font-family: Calibri; mso-bidi-theme-font: minor-latin"&gt;&lt;SPAN style="mso-list: Ignore"&gt;1)&lt;SPAN style="FONT: 7pt 'Times New Roman'"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;You have to have the email server library included/maintained with your project&lt;o:p&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/P&gt;
&lt;P class=MsoListParagraphCxSpMiddle style="MARGIN: 0in 0in 0pt 0.5in; TEXT-INDENT: -0.25in; mso-list: l1 level1 lfo2"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN; mso-bidi-font-family: Calibri; mso-bidi-theme-font: minor-latin"&gt;&lt;SPAN style="mso-list: Ignore"&gt;2)&lt;SPAN style="FONT: 7pt 'Times New Roman'"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;You have to have a system ready to run the email server (i.e. nothing running on the port it uses)&lt;o:p&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/P&gt;
&lt;P class=MsoListParagraphCxSpMiddle style="MARGIN: 0in 0in 0pt 0.5in; TEXT-INDENT: -0.25in; mso-list: l1 level1 lfo2"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN; mso-bidi-font-family: Calibri; mso-bidi-theme-font: minor-latin"&gt;&lt;SPAN style="mso-list: Ignore"&gt;3)&lt;SPAN style="FONT: 7pt 'Times New Roman'"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;you have to have an environment where you won&amp;#8217;t have firewalls&lt;o:p&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/P&gt;
&lt;P class=MsoListParagraphCxSpLast style="MARGIN: 0in 0in 10pt 0.5in; TEXT-INDENT: -0.25in; mso-list: l1 level1 lfo2"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN; mso-bidi-font-family: Calibri; mso-bidi-theme-font: minor-latin"&gt;&lt;SPAN style="mso-list: Ignore"&gt;4)&lt;SPAN style="FONT: 7pt 'Times New Roman'"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;/SPAN&gt;&lt;/SPAN&gt;&lt;/SPAN&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;You have to have TCP running (I know this is pretty common but it is still a prerequisite) &lt;o:p&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/P&gt;
&lt;P class=MsoNormalCxSpFirst&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;FONT face=Arial&gt;&lt;FONT color=#000000&gt;Given all of this baggage and the fact that it doesn't really test anything.. I say that this test does not deserve to be around.&lt;o:p&gt;&lt;/o:p&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/P&gt;
&lt;P class=MsoNormalCxSpMiddle&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;o:p&gt;&lt;FONT face=Arial color=#000000&gt;&amp;nbsp;&lt;/FONT&gt;&lt;/o:p&gt;&lt;/SPAN&gt;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;SPAN lang=EN style="mso-ansi-language: EN"&gt;&lt;FONT face=Calibri&gt;&lt;FONT color=#000000&gt;&lt;FONT face=Arial&gt;What is really scaring me is how this test came into being a unit test using TDD. TDD would have stopped this test ever appearing. &lt;B style="mso-bidi-font-weight: normal"&gt;Where&amp;#8217;s the red bar?&lt;/B&gt; The only way to make the test fail where a mock would not providing you have a working method of sending an email (which was said in that they are using System.Web.Mail) is to change the test or the environment.&lt;/FONT&gt; &lt;o:p&gt;&lt;/o:p&gt;&lt;/FONT&gt;&lt;/FONT&gt;&lt;/SPAN&gt;&lt;/P&gt;
&lt;P class=MsoNormal style="MARGIN: 0in 0in 10pt"&gt;&lt;o:p&gt;&lt;FONT face=Calibri&gt;&amp;nbsp;&lt;/FONT&gt;&lt;/o:p&gt;&lt;/P&gt;&lt;img src="http://geekswithblogs.net/gyoung/aggbug/80292.aspx" width="1" height="1" /&gt;</content>
        <wfw:comment>http://geekswithblogs.net/gyoung/comments/80292.aspx</wfw:comment>
        <slash:comments>5</slash:comments>
        <wfw:commentRss>http://geekswithblogs.net/gyoung/comments/commentRss/80292.aspx</wfw:commentRss>
        <trackback:ping>http://geekswithblogs.net/gyoung/services/trackbacks/80292.aspx</trackback:ping>
    </entry>
    <entry>
        <title>String to Int []</title>
        <link rel="self" type="text/html" href="http://geekswithblogs.net/gyoung/archive/2006/05/29/80056.aspx" />
        <id>http://geekswithblogs.net/gyoung/archive/2006/05/29/80056.aspx</id>
        <published>2006-05-29T21:56:00-05:00:00</published>
        <updated>2006-05-31T12:50:00Z</updated>
        <content type="html">&lt;SPAN style="FONT-FAMILY: Arial"&gt;
&lt;P&gt;&lt;FONT color=#ff0000&gt;I apologize for the code not being indented , I am using word 2007 and no matter what I do it does not seem to want to indent properly (I have tried copy/pasting to notepad, you name it), if you know how to get this working please contact me. See picture of word version &lt;A href="http://geekswithblogs.net/images/geekswithblogs_net/gyoung/4418/r_word.JPG"&gt;http://geekswithblogs.net/images/geekswithblogs_net/gyoung/4418/r_word.JPG &lt;/A&gt;&lt;/FONT&gt;&lt;/P&gt;
&lt;P&gt;&lt;FONT color=#ff0000&gt;&lt;/FONT&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;&lt;FONT color=#ff0000&gt;update I manually indented all of it but I am still wanting to know how to avoid this&lt;/FONT&gt;&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;Everyone seems to enjoy performance posts so &amp;#8230;. I saw this question in the advanced .net group and found it fairly interesting. &lt;/P&gt;
&lt;P&gt;&lt;STRONG&gt;&lt;EM&gt;I have a comma separated list of integer values what's the quickest way to turn this into a integer array. &lt;/EM&gt;&lt;/STRONG&gt;&lt;/P&gt;&lt;/SPAN&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;
&lt;P&gt;Being the geek that I am I set off immediately to find out just how quick I could make an algorithm fly. &lt;/P&gt;
&lt;P&gt;That said let&amp;#8217;s start out with the most obvious answer, we will split the string and call int.Parse() on the string elements. We can use this code to benchmark our other results against. &lt;/P&gt;&lt;/SPAN&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;&lt;SPAN style="FONT-SIZE: 12px; FONT-FAMILY: Courier New"&gt;
&lt;P&gt;&lt;SPAN style="COLOR: blue"&gt;static&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;[] Split(&lt;SPAN style="COLOR: blue"&gt;string&lt;/SPAN&gt; _Numbers) { &lt;BR&gt;&lt;SPAN style="COLOR: blue"&gt;&amp;nbsp; string&lt;/SPAN&gt;[] pieces = _Numbers.Split(&lt;SPAN style="COLOR: maroon"&gt;','&lt;/SPAN&gt;); &lt;BR&gt;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;[] ret = &lt;SPAN style="COLOR: blue"&gt;new&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;[pieces.Length]; &lt;BR&gt;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;for&lt;/SPAN&gt; (&lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt; i = 0; i &amp;lt; pieces.Length; i++) { &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; ret[i] = &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;.Parse(pieces[i]);&amp;nbsp;&lt;BR&gt;&amp;nbsp;&amp;nbsp;}&amp;nbsp;&lt;BR&gt;&amp;nbsp;&amp;nbsp;&lt;SPAN style="COLOR: blue"&gt;return&lt;/SPAN&gt; ret; &lt;BR&gt;}&lt;/P&gt;&lt;/SPAN&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;
&lt;P&gt;Next we will need some data to feed into the routine. I chose &lt;SPAN style="COLOR: maroon"&gt;"1,2,3,4,5,6,7,8,9,10,121,1000,10000" &lt;/SPAN&gt;as my testing data. Running through this data 1,000,000 times takes a total of 4.39 seconds on my system (in release mode). I think that we can do better than this!! &lt;/P&gt;
&lt;P&gt;Using an old trick I figured that I would just make the string a char [] and iterate through it taking my current number and subtracting its char code from &amp;#8216;0&amp;#8217; (it just so happens that &amp;#8216;9&amp;#8217; &amp;#8211; &amp;#8216;0&amp;#8217; = 9 how convenient! Applying this methodology leaves us with the following code. &lt;/P&gt;&lt;/SPAN&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;&lt;SPAN style="FONT-SIZE: 12px; FONT-FAMILY: Courier New"&gt;
&lt;P&gt;&lt;SPAN style="COLOR: blue"&gt;static&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;[] Iterate(&lt;SPAN style="COLOR: blue"&gt;string&lt;/SPAN&gt; _Numbers, &lt;SPAN style="COLOR: blue"&gt;ref&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt; _Count) { &lt;BR&gt;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;[] buffer = &lt;SPAN style="COLOR: blue"&gt;new&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;[4]; &lt;BR&gt;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;char&lt;/SPAN&gt;[] chars = _Numbers.ToCharArray(); &lt;BR&gt;&amp;nbsp; _Count = 0;&amp;nbsp; &lt;BR&gt;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt; holder = 0;&amp;nbsp;&lt;BR&gt;&amp;nbsp;&amp;nbsp;&lt;SPAN style="COLOR: blue"&gt;for&lt;/SPAN&gt; (&lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt; i = 0; i &amp;lt; chars.Length; i++) { &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;if&lt;/SPAN&gt; (chars[i] == &lt;SPAN style="COLOR: maroon"&gt;','&lt;/SPAN&gt;) { &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; buffer[_Count] = holder; &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; holder = 0;&amp;nbsp;&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; _Count++; &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;if&lt;/SPAN&gt; (_Count == buffer.Length) { &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;[] tmp = buffer;&amp;nbsp;&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;buffer = &lt;SPAN style="COLOR: blue"&gt;new&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;[tmp.Length * 2];&amp;nbsp;&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;SPAN style="COLOR: teal"&gt;Buffer&lt;/SPAN&gt;.BlockCopy(tmp, 0, buffer, 0, tmp.Length * 4); &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; } &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; } &lt;SPAN style="COLOR: blue"&gt;else &lt;/SPAN&gt;{ &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; holder = holder * 10 + chars[i] - &lt;SPAN style="COLOR: maroon"&gt;'0'&lt;/SPAN&gt;;&amp;nbsp;&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;} &lt;BR&gt;&amp;nbsp; }&amp;nbsp;&lt;BR&gt;&amp;nbsp;&amp;nbsp;&lt;SPAN style="COLOR: blue"&gt;return&lt;/SPAN&gt; buffer; &lt;BR&gt;}&lt;/P&gt;&lt;/SPAN&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;
&lt;P&gt;This code also has some oddities involved with it since it does not know initially the size of the int [] that it needs to pass back. In order to support this, it grows it&amp;#8217;s int [] as it needs to (by doubling). This can be an expensive operation so avoiding it is best. Also since it is doubling its array, it has a new parameter Count which it uses to return the total number of elements in the array it returns (it may return a 32 element array that only uses 18 elements). &lt;/P&gt;
&lt;P&gt;As for performance, the exact code above will handle the same data as our first test in &amp;lt;&amp;gt; .5 seconds on my machine with a buffer size of 4. Not bad 10% of our first try! To show the importance of the buffer though, if we make the initial size 16 the code finishes in .4 seconds! &lt;/P&gt;
&lt;P&gt;There are still some areas we can optimize though. Keep in mind that this code is creating 1,000,000 char []. This is a pretty expensive operation, by using unsafe code we can avoid doing this. Here is the code &lt;/P&gt;&lt;/SPAN&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;&lt;SPAN style="FONT-SIZE: 12px; FONT-FAMILY: Courier New"&gt;
&lt;P&gt;&lt;SPAN style="COLOR: blue"&gt;static&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;unsafe&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;[] Unsafe1(&lt;SPAN style="COLOR: blue"&gt;string&lt;/SPAN&gt; _Numbers, &lt;SPAN style="COLOR: blue"&gt;ref&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt; _Count) { &lt;BR&gt;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;[] buffer = &lt;SPAN style="COLOR: blue"&gt;new&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;[64]; &lt;BR&gt;&amp;nbsp; _Count = 0; &lt;BR&gt;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt; total = _Numbers.Length; &lt;BR&gt;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt; holder = 0; &lt;BR&gt;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;fixed&lt;/SPAN&gt; (&lt;SPAN style="COLOR: blue"&gt;char&lt;/SPAN&gt;* a = _Numbers) { &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;char&lt;/SPAN&gt;* c = a; &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;while&lt;/SPAN&gt; (total &amp;gt; 0) {&amp;nbsp;&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;SPAN style="COLOR: blue"&gt;if&lt;/SPAN&gt; (*c == &lt;SPAN style="COLOR: maroon"&gt;','&lt;/SPAN&gt;) { &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; buffer[_Count] = holder; &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; holder = 0; &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; _Count++; &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;if&lt;/SPAN&gt; (_Count == buffer.Length) { &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;[] tmp = buffer; &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; buffer = &lt;SPAN style="COLOR: blue"&gt;new&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;[tmp.Length * 2]; &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: teal"&gt;Buffer&lt;/SPAN&gt;.BlockCopy(tmp, 0, buffer, 0, tmp.Length * 4); &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; } &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&amp;nbsp;&lt;SPAN style="COLOR: blue"&gt;else &lt;/SPAN&gt;{&amp;nbsp;&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;holder = holder * 10 + *c - &lt;SPAN style="COLOR: maroon"&gt;'0'&lt;/SPAN&gt;; &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&amp;nbsp;&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;c++; &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; total--; &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; } &lt;BR&gt;&amp;nbsp; } &lt;BR&gt;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;return&lt;/SPAN&gt; buffer; &lt;BR&gt;}&lt;/P&gt;&lt;/SPAN&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;
&lt;P&gt;Again we use the same buffering mechanism that we used on the last entry. The main difference here is that instead of creating a char [] we use unsafe code to iterate through the string. With a buffer size of 16, this code runs through the 1,000,000 iterations in .37. &lt;/P&gt;
&lt;P&gt;&lt;EM&gt;In running these, many of you may notice that for small bits of data that the iterate function may actually run faster than the unsafe code. This can be the case but as you add more data, the gap will grow larger in the favor of the unsafe code (it also uses less memory as it does not duplicate the memory from the original string). &lt;/EM&gt;&lt;/P&gt;
&lt;P&gt;&lt;STRONG&gt;Use the framework Luke! &lt;/STRONG&gt;&lt;/P&gt;
&lt;P&gt;We have had one problem thus far with our code, its ugly. Having to get back an array then use a separate counter from the length of the array to loop is .. well ugly. As an example consider the following. &lt;/P&gt;&lt;/SPAN&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;&lt;SPAN style="FONT-SIZE: 12px; FONT-FAMILY: Courier New"&gt;
&lt;P&gt;&lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt; foo = 0; &lt;BR&gt;&lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt; [] values = Iterate(numbers, &lt;SPAN style="COLOR: blue"&gt;ref&lt;/SPAN&gt; foo); &lt;/P&gt;
&lt;P&gt;&lt;SPAN style="COLOR: blue"&gt;for&lt;/SPAN&gt; (&lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt; i = 0; i &amp;lt; foo; i++) { &lt;/P&gt;
&lt;P&gt;} &lt;/P&gt;
&lt;P&gt;&lt;SPAN style="COLOR: green"&gt;//CANT DO &lt;/SPAN&gt;&lt;/P&gt;
&lt;P&gt;&lt;SPAN style="COLOR: blue"&gt;for&lt;/SPAN&gt; (&lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt; i = 0; i &amp;lt; values.Length; i++) { &lt;/P&gt;
&lt;P&gt;}&lt;/P&gt;&lt;/SPAN&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;Personally I prefer the second way of doing this was it makes more sense to programmers. Luckily generics in the framework can do just this for us. By changing our return type from an int [] to a generic list we can keep most of the speed and offer a better interface. &lt;/SPAN&gt;&lt;/P&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;&lt;SPAN style="FONT-SIZE: 12px; FONT-FAMILY: Courier New"&gt;
&lt;P&gt;&lt;SPAN style="COLOR: blue"&gt;static&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;unsafe&lt;/SPAN&gt; &lt;SPAN style="COLOR: teal"&gt;List&lt;/SPAN&gt;&amp;lt;&lt;SPAN style="COLOR: teal"&gt;Int32&lt;/SPAN&gt;&amp;gt; UseGeneric(&lt;SPAN style="COLOR: blue"&gt;string&lt;/SPAN&gt; _Numbers) { &lt;BR&gt;&lt;SPAN style="COLOR: teal"&gt;&amp;nbsp; List&lt;/SPAN&gt;&amp;lt;&lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;&amp;gt; ret = &lt;SPAN style="COLOR: blue"&gt;new&lt;/SPAN&gt; &lt;SPAN style="COLOR: teal"&gt;List&lt;/SPAN&gt;&amp;lt;&lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;&amp;gt;(64); &lt;BR&gt;&lt;SPAN style="COLOR: blue"&gt;&amp;nbsp; int&lt;/SPAN&gt; total = _Numbers.Length; &lt;BR&gt;&lt;SPAN style="COLOR: blue"&gt;&amp;nbsp; int&lt;/SPAN&gt; tmp = 0; &lt;/P&gt;
&lt;P&gt;&lt;SPAN style="COLOR: blue"&gt;&amp;nbsp; fixed&lt;/SPAN&gt; (&lt;SPAN style="COLOR: blue"&gt;char&lt;/SPAN&gt;* a = _Numbers) { &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;char&lt;/SPAN&gt;* c = a; &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;while&lt;/SPAN&gt; (total &amp;gt; 0) { &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;if&lt;/SPAN&gt; (*c == &lt;SPAN style="COLOR: maroon"&gt;','&lt;/SPAN&gt;) { &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ret.Add(tmp); &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; tmp = 0;&amp;nbsp;&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;} &lt;SPAN style="COLOR: blue"&gt;else &lt;/SPAN&gt;{ &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; tmp = tmp * 10 + *c - &lt;SPAN style="COLOR: maroon"&gt;'0'&lt;/SPAN&gt;; &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; } &lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; total--; &lt;BR&gt;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; c++;&amp;nbsp;&lt;BR&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&amp;nbsp;&lt;BR&gt;&amp;nbsp;&amp;nbsp;} &lt;BR&gt;&amp;nbsp; &lt;SPAN style="COLOR: blue"&gt;return&lt;/SPAN&gt; ret; &lt;BR&gt;}&lt;/P&gt;&lt;/SPAN&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;
&lt;P&gt;This is a much nicer interface than what we had before and is still very performant. 1,000,000 iterations with this takes approximately the same time as out unsafe example! The reason this works about the same as our first example, is because it does pretty much the same thing internally with it&amp;#8217;s buffer as what we were implementing on our own (of course, it does a much nicer job encapsulating it than we were so this is probably the best overall solution). Basically as you add items, it also doubles it's internal array size then copies over the old data in order to allow you to continue adding data.&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;Another solution which was offered up in the discussion by &lt;A href="http://dotnet.org.za/ernst"&gt;Ernst Kuschke&lt;/A&gt; is syntactical sugar (although not very performant) so I figured it was definitely worth including simply for its elegance (and it should probably be a good general method for doing this. Sugar like this is always more maintainable, converting this to support doubles or another type would be a lot easier than our other examples. &lt;/P&gt;&lt;/SPAN&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;&lt;SPAN style="FONT-SIZE: 12px; FONT-FAMILY: Courier New"&gt;
&lt;P&gt;&lt;SPAN style="COLOR: blue"&gt;public&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;static&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;[] doTheThing(&lt;SPAN style="COLOR: blue"&gt;string&lt;/SPAN&gt; commadelimitedInts) {&lt;BR&gt;&lt;SPAN style="COLOR: blue"&gt;&amp;nbsp; return&lt;/SPAN&gt; &lt;SPAN style="COLOR: teal"&gt;Array&lt;/SPAN&gt;.ConvertAll&amp;lt;&lt;SPAN style="COLOR: blue"&gt;string&lt;/SPAN&gt;, &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;&amp;gt;(commadelimitedInts.Split(&lt;SPAN style="COLOR: blue"&gt;new&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;string&lt;/SPAN&gt;[] { &lt;SPAN style="COLOR: maroon"&gt;","&lt;/SPAN&gt; }, &lt;SPAN style="COLOR: teal"&gt;StringSplitOptions&lt;/SPAN&gt;.RemoveEmptyEntries), &lt;SPAN style="COLOR: blue"&gt;new&lt;/SPAN&gt; &lt;SPAN style="COLOR: teal"&gt;Converter&lt;/SPAN&gt;&amp;lt;&lt;SPAN style="COLOR: blue"&gt;string&lt;/SPAN&gt;, &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;&amp;gt;(intToString)); &lt;BR&gt;} &lt;/SPAN&gt;&lt;/P&gt;&lt;SPAN style="FONT-SIZE: 12px; FONT-FAMILY: Courier New"&gt;
&lt;P&gt;&lt;SPAN style="COLOR: blue"&gt;public&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;static&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt; intToString(&lt;SPAN style="COLOR: blue"&gt;string&lt;/SPAN&gt; strInt) { &lt;BR&gt;&lt;SPAN style="COLOR: blue"&gt;&amp;nbsp; int&lt;/SPAN&gt; i; &lt;BR&gt;&lt;SPAN style="COLOR: blue"&gt;&amp;nbsp; int&lt;/SPAN&gt;.TryParse(strInt, &lt;SPAN style="COLOR: blue"&gt;out&lt;/SPAN&gt; i); &lt;BR&gt;&lt;SPAN style="COLOR: blue"&gt;&amp;nbsp; return&lt;/SPAN&gt; i; &lt;BR&gt;}&lt;/P&gt;&lt;/SPAN&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;
&lt;P&gt;Ernst takes advantage of the ConvertAll method to produce a very short bit of code that does the task. It has performance characteristics similar to our baseline as well (while being significantly shorter). If performance is not you main goal (it is quite rare that we are doing millions of theses transforms in an application), this is definitely the way to go as it is quite maintainable. &lt;/P&gt;
&lt;P&gt;&lt;FONT color=#ff0000&gt;Update: Ernst's friend &lt;A href="http://dotnet.org.za/piers/default.aspx"&gt;Piers&lt;/A&gt;&amp;nbsp;came up with an even more elegant method of calling this&lt;/FONT&gt;&lt;/P&gt;
&lt;P&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;&lt;SPAN style="FONT-SIZE: 12px; FONT-FAMILY: Courier New"&gt;
&lt;P&gt;&lt;SPAN style="COLOR: blue"&gt;public&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;static&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;[] doTheThing(&lt;SPAN style="COLOR: blue"&gt;string&lt;/SPAN&gt; commadelimitedInts) {&lt;BR&gt;&lt;SPAN style="COLOR: blue"&gt;&amp;nbsp; return&lt;/SPAN&gt; &lt;SPAN style="COLOR: teal"&gt;Array&lt;/SPAN&gt;.ConvertAll&amp;lt;&lt;SPAN style="COLOR: blue"&gt;string&lt;/SPAN&gt;, &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;&amp;gt;(commadelimitedInts.Split(&lt;SPAN style="COLOR: blue"&gt;new&lt;/SPAN&gt; &lt;SPAN style="COLOR: blue"&gt;string&lt;/SPAN&gt;[] { &lt;SPAN style="COLOR: maroon"&gt;","&lt;/SPAN&gt; }, &lt;SPAN style="COLOR: teal"&gt;StringSplitOptions&lt;/SPAN&gt;.RemoveEmptyEntries), &lt;SPAN style="COLOR: blue"&gt;new&lt;/SPAN&gt; &lt;SPAN style="COLOR: teal"&gt;Converter&lt;/SPAN&gt;&amp;lt;&lt;SPAN style="COLOR: blue"&gt;string&lt;/SPAN&gt;, &lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;&amp;gt;(System.&lt;SPAN style="FONT-SIZE: 12px; FONT-FAMILY: Courier New"&gt;&lt;SPAN style="COLOR: teal"&gt;Convert&lt;/SPAN&gt;.&lt;/SPAN&gt;&lt;SPAN style="FONT-SIZE: 12px; FONT-FAMILY: Courier New"&gt;ToInt32)&lt;/SPAN&gt;); &lt;BR&gt;} &lt;/SPAN&gt;&lt;SPAN style="FONT-SIZE: 12px; FONT-FAMILY: Courier New"&gt;&lt;/P&gt;&lt;/SPAN&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/P&gt;
&lt;P&gt;The elegance of this solution is definitely apparent!&lt;/P&gt;
&lt;P&gt;Now to put our various solutions to the real test I have made a big string [1..1000] that we will run through 1,000,000 times. All algorithms that use array growing will be seeded with an initial buffer size of 64 to make things fair between them while also forcing their weakness of having to grow the buffer a few times. &lt;/P&gt;&lt;/SPAN&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 367px"&gt;
&lt;COL style="WIDTH: 367px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P align=center&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;Algorithm&lt;/SPAN&gt;&lt;/P&gt;&lt;/TD&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: medium none; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P align=center&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;Execution Time&lt;/SPAN&gt;&lt;/P&gt;&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: medium none; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;Split (Base Line)&lt;/SPAN&gt;&lt;/P&gt;&lt;/TD&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: medium none; PADDING-LEFT: 7px; BORDER-LEFT: medium none; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;00:05:42:703&lt;/SPAN&gt;&lt;/P&gt;&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: medium none; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;Syntactic Sugar with Delegate&lt;/SPAN&gt;&lt;/P&gt;&lt;/TD&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: medium none; PADDING-LEFT: 7px; BORDER-LEFT: medium none; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;00:06:36:703&lt;/SPAN&gt;&lt;/P&gt;&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: medium none; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;Iteration&lt;/SPAN&gt;&lt;/P&gt;&lt;/TD&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: medium none; PADDING-LEFT: 7px; BORDER-LEFT: medium none; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;00:00:22.312&lt;/SPAN&gt;&lt;/P&gt;&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: medium none; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;Unsafe&lt;/SPAN&gt;&lt;/P&gt;&lt;/TD&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: medium none; PADDING-LEFT: 7px; BORDER-LEFT: medium none; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;00:00:16.90625&lt;/SPAN&gt;&lt;/P&gt;&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: medium none; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;Unsafe with generic return&lt;/SPAN&gt;&lt;/P&gt;&lt;/TD&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: medium none; PADDING-LEFT: 7px; BORDER-LEFT: medium none; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;00:00:18.937&lt;/SPAN&gt;&lt;/P&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;
&lt;P&gt;&lt;STRONG&gt;Analysis &lt;/STRONG&gt;&lt;/P&gt;
&lt;P&gt;As you can see performance for our base line (simple split) and the delegate method completely degrade under larger values as one would expect. As I mentioned earlier, the unsafe methods squeaked ahead of the iteration due to not having to create the char array. Of course, the real winner here is the generic return coming in second who makes our code readable, and extremely fast. &lt;/P&gt;
&lt;P&gt;Can you come up with an algorithm for this problem? Post it here! &lt;/P&gt;&lt;/SPAN&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;&lt;SPAN style="FONT-FAMILY: Arial"&gt;&lt;/SPAN&gt;&amp;nbsp;&lt;/P&gt;&lt;img src="http://geekswithblogs.net/gyoung/aggbug/80056.aspx" width="1" height="1" /&gt;</content>
        <wfw:comment>http://geekswithblogs.net/gyoung/comments/80056.aspx</wfw:comment>
        <slash:comments>11</slash:comments>
        <wfw:commentRss>http://geekswithblogs.net/gyoung/comments/commentRss/80056.aspx</wfw:commentRss>
        <trackback:ping>http://geekswithblogs.net/gyoung/services/trackbacks/80056.aspx</trackback:ping>
    </entry>
    <entry>
        <title>Floating Point Fun</title>
        <link rel="self" type="text/html" href="http://geekswithblogs.net/gyoung/archive/2006/05/30/80119.aspx" />
        <id>http://geekswithblogs.net/gyoung/archive/2006/05/30/80119.aspx</id>
        <published>2006-05-30T12:35:00-05:00:00</published>
        <updated>2006-05-30T20:03:00Z</updated>
        <content type="html">&lt;P&gt;I am sure by now that most know how floating point approximations work on a computer.. They can be &lt;STRONG&gt;quite &lt;/STRONG&gt;interesting. This has to to be the weirdest experience I have ever had with them though &lt;/P&gt;
&lt;P&gt;Open a new console application in .NET 2.0 (set to build in release mode /debug:pdbonly should be the default) it is important for me to note that all of this code runs fine in 1.x.&lt;/P&gt;
&lt;P&gt;Paste the following code into your main function &lt;/P&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;&lt;SPAN style="FONT-SIZE: 10px; FONT-FAMILY: Courier New"&gt;
&lt;P&gt;&lt;FONT size=3&gt;&lt;SPAN style="COLOR: blue"&gt;float&lt;/SPAN&gt; f = 97.09f; &lt;BR&gt;&lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt; tmp = (int) (f * 100.0f); &lt;BR&gt;&lt;SPAN style="COLOR: teal"&gt;Console&lt;/SPAN&gt;.WriteLine(tmp);&lt;/FONT&gt;&lt;/P&gt;&lt;/SPAN&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;&lt;STRONG&gt;Output: 9708 &lt;/STRONG&gt;&lt;/P&gt;
&lt;P&gt;Interesting eh? It gets more interesting! &lt;/P&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;&lt;SPAN style="FONT-SIZE: 10px; FONT-FAMILY: Courier New"&gt;
&lt;P&gt;&lt;FONT size=3&gt;&lt;SPAN style="COLOR: blue"&gt;float&lt;/SPAN&gt; f = 97.09f; &lt;BR&gt;&lt;SPAN style="COLOR: blue"&gt;float&lt;/SPAN&gt; tmp = f * 100.0f; &lt;BR&gt;&lt;SPAN style="COLOR: teal"&gt;Console&lt;/SPAN&gt;.WriteLine(tmp);&lt;/FONT&gt;&lt;/P&gt;&lt;/SPAN&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;&lt;STRONG&gt;Output: 9709 &lt;/STRONG&gt;&lt;/P&gt;
&lt;P&gt;This is very interesting when taken in context with the operation above. Let&amp;#8217;s stop for a minute and think about what we said should happen. We told it to take f and multiply It by 100.0 storing the intermediate result as a floating point, and to then take that floating point and convert it to an integer. When we run the second example, we can see that if we do the operation as a floating point, it comes out correctly. So where is the disconnect? &lt;/P&gt;
&lt;P&gt;Let&amp;#8217;s try to explicitly tell the compiler what we want to do. &lt;/P&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;&lt;SPAN style="FONT-SIZE: 10px; FONT-FAMILY: Courier New"&gt;
&lt;P&gt;&lt;FONT size=3&gt;&lt;SPAN style="COLOR: blue"&gt;float&lt;/SPAN&gt; f = 97.09f; &lt;BR&gt;f = (f * 100f); &lt;BR&gt;&lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt; tmp = (&lt;SPAN style="COLOR: blue"&gt;int&lt;/SPAN&gt;)f; &lt;BR&gt;&lt;SPAN style="COLOR: teal"&gt;Console&lt;/SPAN&gt;.WriteLine(tmp);&lt;/FONT&gt;&lt;/P&gt;&lt;/SPAN&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;&lt;STRONG&gt;Output: 9709 (with a debugger attached, 9708 without in release mode!!) DEBUG:PDBONLY (even with no debug information through advanced settings) &lt;/STRONG&gt;&lt;/P&gt;
&lt;P&gt;Wow this has become &lt;STRONG&gt;REALLY &lt;/STRONG&gt;interesting. What on earth happened here? &lt;/P&gt;
&lt;P&gt;Let&amp;#8217;s look at some IL to get a better idea of what&amp;#8217;s going on here. &lt;/P&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;&lt;SPAN style="COLOR: #1000a0"&gt;.locals&lt;/SPAN&gt; &lt;SPAN style="COLOR: #1000a0"&gt;init&lt;/SPAN&gt; ( &lt;BR&gt;[&lt;SPAN style="COLOR: maroon"&gt;0&lt;/SPAN&gt;] &lt;A title=float32 href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=3"&gt;float32&lt;/A&gt; &lt;STRONG&gt;single1&lt;/STRONG&gt;, &lt;BR&gt;[&lt;SPAN style="COLOR: maroon"&gt;1&lt;/SPAN&gt;] &lt;A title=float32 href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=4"&gt;float32&lt;/A&gt; &lt;STRONG&gt;single2&lt;/STRONG&gt;) &lt;BR&gt;L_0000: ldc.r4 &lt;SPAN style="COLOR: maroon"&gt;97.09&lt;/SPAN&gt; &lt;BR&gt;L_0005: stloc.0 &lt;BR&gt;L_0006: ldloc.0 &lt;BR&gt;L_0007: ldc.r4 &lt;SPAN style="COLOR: maroon"&gt;100&lt;/SPAN&gt; &lt;BR&gt;L_000c: mul &lt;BR&gt;L_000d: stloc.1 &lt;BR&gt;L_000e: ldloc.1 &lt;BR&gt;L_000f: call &lt;A title=void href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=5"&gt;void&lt;/A&gt; [&lt;A title="mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=6"&gt;mscorlib&lt;/A&gt;]&lt;A title=System.Console href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=7"&gt;System.Console&lt;/A&gt;::&lt;A title=WriteLine href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=8"&gt;WriteLine&lt;/A&gt;(&lt;A title=float32 href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=9"&gt;float32&lt;/A&gt;) &lt;BR&gt;L_0014: ret &lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: medium none; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;This is our floating point example that prints the correct value (as a float)&lt;/P&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;&lt;SPAN style="COLOR: #1000a0"&gt;.locals&lt;/SPAN&gt; &lt;SPAN style="COLOR: #1000a0"&gt;init&lt;/SPAN&gt; ( &lt;BR&gt;[&lt;SPAN style="COLOR: maroon"&gt;0&lt;/SPAN&gt;] &lt;A title=float32 href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=3"&gt;float32&lt;/A&gt; &lt;STRONG&gt;single1&lt;/STRONG&gt;, &lt;BR&gt;[&lt;SPAN style="COLOR: maroon"&gt;1&lt;/SPAN&gt;] &lt;A title=int32 href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=4"&gt;int32&lt;/A&gt; &lt;STRONG&gt;num1&lt;/STRONG&gt;) &lt;BR&gt;L_0000: ldc.r4 &lt;SPAN style="COLOR: maroon"&gt;97.09&lt;/SPAN&gt; &lt;BR&gt;L_0005: stloc.0 &lt;BR&gt;L_0006: ldloc.0 &lt;BR&gt;L_0007: ldc.r4 &lt;SPAN style="COLOR: maroon"&gt;100&lt;/SPAN&gt; &lt;BR&gt;L_000c: mul &lt;BR&gt;L_000d: conv.i4 &lt;BR&gt;L_000e: stloc.1 &lt;BR&gt;L_000f: ldloc.1 &lt;BR&gt;L_0010: call &lt;A title=void href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=5"&gt;void&lt;/A&gt; [&lt;A title="mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=6"&gt;mscorlib&lt;/A&gt;]&lt;A title=System.Console href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=7"&gt;System.Console&lt;/A&gt;::&lt;A title=WriteLine href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=8"&gt;WriteLine&lt;/A&gt;(&lt;A title=int32 href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=9"&gt;int32&lt;/A&gt;) &lt;BR&gt;L_0015: ret &lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: medium none; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;This is our floating point example that came out wrong above&lt;/P&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;&lt;SPAN style="COLOR: #1000a0"&gt;.locals&lt;/SPAN&gt; &lt;SPAN style="COLOR: #1000a0"&gt;init&lt;/SPAN&gt; ( &lt;BR&gt;[&lt;SPAN style="COLOR: maroon"&gt;0&lt;/SPAN&gt;] &lt;A title=float32 href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=3"&gt;float32&lt;/A&gt; &lt;STRONG&gt;single1&lt;/STRONG&gt;, &lt;BR&gt;[&lt;SPAN style="COLOR: maroon"&gt;1&lt;/SPAN&gt;] &lt;A title=int32 href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=4"&gt;int32&lt;/A&gt; &lt;STRONG&gt;num1&lt;/STRONG&gt;) &lt;BR&gt;L_0000: ldc.r4 &lt;SPAN style="COLOR: maroon"&gt;97.09&lt;/SPAN&gt; &lt;BR&gt;L_0005: stloc.0 &lt;BR&gt;L_0006: ldloc.0 &lt;BR&gt;L_0007: ldc.r4 &lt;SPAN style="COLOR: maroon"&gt;100&lt;/SPAN&gt; &lt;BR&gt;L_000c: mul &lt;BR&gt;L_000d: stloc.0 &lt;BR&gt;L_000e: ldloc.0 &lt;BR&gt;L_000f: conv.i4 &lt;BR&gt;L_0010: stloc.1 &lt;BR&gt;L_0011: ldloc.1 &lt;BR&gt;L_0012: call &lt;A title=void href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=5"&gt;void&lt;/A&gt; [&lt;A title="mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=6"&gt;mscorlib&lt;/A&gt;]&lt;A title=System.Console href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=7"&gt;System.Console&lt;/A&gt;::&lt;A title=WriteLine href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=8"&gt;WriteLine&lt;/A&gt;(&lt;A title=int32 href="http://www.aisto.com/roeder/dotnet/Default.aspx?Object=9"&gt;int32&lt;/A&gt;) &lt;BR&gt;L_0017: ret &lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: medium none; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;This is our floating point example that gets it right when debugger is attached but not without&lt;/P&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;Interesting, the only significant difference between the one that never works and the one that does but only in when a debugger is attached is that the one that does work stores and then loads our value back onto the stack before issuing the conv.i4 on the value. &lt;/P&gt;
&lt;P&gt;L_000c: mul &lt;BR&gt;&lt;SPAN style="BACKGROUND-COLOR: yellow"&gt;L_000d: stloc.0 &lt;BR&gt;&lt;/SPAN&gt;&lt;SPAN style="BACKGROUND-COLOR: yellow"&gt;L_000e: ldloc.0&lt;/SPAN&gt; &lt;BR&gt;L_000f: conv.i4 &lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;Basically these instructions are telling it to take the result from the multiplication (pop it off of the stack) and store them back into location0 which is our floating point variable. It then says to take that floating point variable and push it onto the stack so it can be used for the cast operation. This is probably something that should be handled for us (by the C# compiler) in the case of our first example so that it works as well as the 3&lt;SUP&gt;rd&lt;/SUP&gt; example. &lt;/P&gt;
&lt;P&gt;The &amp;#8220;debugger/no debugger&amp;#8221; problem is still our big problem though. The fact that JIT optimizations are changing behavior of identical IL is frankly kind of scary. My initial thought upon seeing the changes we just identified was that the operation was being optimized away by the JIT (storing and loading the same value on the stack seems like just the thing the JIT optimizer would be looking for) thus causing the problem. &lt;/P&gt;
&lt;P&gt;The next step in tracking this down will be to look at the native code being generated. &lt;/P&gt;
&lt;P&gt;Note: In order to do this you have to enable &amp;#8220;Native Debugging&amp;#8221; in Visual Studio. &lt;/P&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;&lt;SPAN style="FONT-FAMILY: Courier New"&gt;
&lt;P&gt;00000000 push esi &lt;BR&gt;00000001 sub esp,8 &lt;BR&gt;00000004 fld dword ptr ds:[00C400D0h] &lt;BR&gt;0000000a fld dword ptr ds:[00C400D4h] &lt;BR&gt;00000010 fmulp st(1),st &lt;BR&gt;00000012 fstp qword ptr [esp] &lt;BR&gt;00000015 fld qword ptr [esp] &lt;BR&gt;00000018 fstp qword ptr [esp] &lt;BR&gt;0000001b movsd xmm0,mmword ptr [esp] &lt;BR&gt;00000020 cvttsd2si esi,xmm0 &lt;BR&gt;00000024 cmp dword ptr ds:[02271084h],0 &lt;BR&gt;0000002b jne 00000037 &lt;BR&gt;0000002d mov ecx,1 &lt;BR&gt;00000032 call 7870D79C &lt;BR&gt;00000037 mov ecx,dword ptr ds:[02271084h] &lt;BR&gt;0000003d mov edx,esi &lt;BR&gt;0000003f mov eax,dword ptr [ecx] &lt;BR&gt;00000041 call dword ptr [eax+000000BCh] &lt;BR&gt;00000047 call 78776B48 &lt;BR&gt;0000004c mov ecx,eax &lt;BR&gt;0000004e mov eax,dword ptr [ecx] &lt;BR&gt;00000050 call dword ptr [eax+64h] &lt;BR&gt;00000053 add esp,8 &lt;BR&gt;00000056 pop esi &lt;BR&gt;00000057 ret &lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;&lt;/SPAN&gt;&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: medium none; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;This is our native code when started without the debugger (attach to process when its running) &lt;STRONG&gt;9708&lt;/STRONG&gt;&lt;/P&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;DIV&gt;
&lt;TABLE style="BORDER-COLLAPSE: collapse" border=0&gt;
&lt;COLGROUP&gt;
&lt;COL style="WIDTH: 734px"&gt;&lt;/COLGROUP&gt;
&lt;TBODY vAlign=top&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: black 0.5pt solid; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;&lt;SPAN style="FONT-FAMILY: Courier New"&gt;
&lt;P&gt;00000000 push esi &lt;BR&gt;00000001 sub esp,10h &lt;BR&gt;00000004 mov dword ptr [esp],ecx &lt;BR&gt;00000007 cmp dword ptr ds:[00918868h],0 &lt;BR&gt;0000000e je 00000015 &lt;BR&gt;00000010 call 79441146 &lt;BR&gt;00000015 fldz &lt;BR&gt;00000017 fstp dword ptr [esp+4] &lt;BR&gt;0000001b xor esi,esi &lt;BR&gt;0000001d mov dword ptr [esp+4],42C22E14h &lt;BR&gt;00000025 fld dword ptr ds:[00C51214h] &lt;BR&gt;0000002b fmul dword ptr [esp+4] &lt;BR&gt;0000002f fstp dword ptr [esp+4] &lt;BR&gt;00000033 fld dword ptr [esp+4] &lt;BR&gt;00000037 fstp qword ptr [esp+8] &lt;BR&gt;0000003b movsd xmm0,mmword ptr [esp+8] &lt;BR&gt;00000041 cvttsd2si eax,xmm0 &lt;BR&gt;00000045 mov esi,eax &lt;BR&gt;00000047 mov ecx,esi &lt;BR&gt;00000049 call 78767DE4 &lt;BR&gt;0000004e call 78767BBC &lt;BR&gt;00000053 nop &lt;BR&gt;00000054 nop &lt;BR&gt;00000055 add esp,10h &lt;BR&gt;00000058 pop esi &lt;BR&gt;00000059 ret &lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;&lt;/SPAN&gt;&lt;/TD&gt;&lt;/TR&gt;
&lt;TR&gt;
&lt;TD style="BORDER-RIGHT: black 0.5pt solid; PADDING-RIGHT: 7px; BORDER-TOP: medium none; PADDING-LEFT: 7px; BORDER-LEFT: black 0.5pt solid; BORDER-BOTTOM: black 0.5pt solid"&gt;
&lt;P&gt;This is our native code when started with the debugger &lt;STRONG&gt;9709&lt;/STRONG&gt; &lt;/P&gt;
&lt;P&gt;(I am fairly certain this disables at least some forms of JIT optimizations) &lt;/P&gt;&lt;/TD&gt;&lt;/TR&gt;&lt;/TBODY&gt;&lt;/TABLE&gt;&lt;/DIV&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;Unfortunately when looking at the native code it does not appear that this push/pop is being removed. I have to admit that I am &lt;STRONG&gt;very &lt;/STRONG&gt;rusty on my assembly language but my uneducated guess here would be that the difference is being seen due to the change from dword values to qword values . In the version that does not work, the operation is being done on QWORD values, in the version that does work it is being done on DWORD values. &lt;/P&gt;
&lt;P&gt;If we look we can see that in the working example, it is done in dwords; then changed to be a qword &lt;/P&gt;&lt;SPAN style="FONT-FAMILY: Courier New"&gt;
&lt;P&gt;0000002b fmul dword ptr [esp+4] &lt;BR&gt;0000002f fstp dword ptr [esp+4] &lt;BR&gt;00000033 fld dword ptr [esp+4] &lt;BR&gt;&lt;SPAN style="BACKGROUND-COLOR: yellow"&gt;00000037 fstp qword ptr [esp+8]&lt;/SPAN&gt; &lt;/P&gt;&lt;/SPAN&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;In the non-working example all operations are done with qwords &lt;/P&gt;&lt;SPAN style="FONT-FAMILY: Courier New"&gt;
&lt;P&gt;00000010 fmulp st(1),st &lt;BR&gt;00000012 fstp qword ptr [esp] &lt;BR&gt;00000015 fld qword ptr [esp] &lt;BR&gt;00000018 fstp qword ptr [esp] &lt;/P&gt;&lt;/SPAN&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;My (again &lt;STRONG&gt;uneducated)&lt;/STRONG&gt; guess is that what is happening is that the higher precision of the qword is picking up a small residual causing the result to be off (just slightly i.e. 98.9999999997). This could easily cause the behavior being seen. &lt;/P&gt;
&lt;P&gt;Basically this is not so much a bug, as it is an oddity. The CLR is treating floats internally (when its time to do calculations) as if they were&amp;nbsp;float64s (I would imagine since context switching from floating point to MMX is kind slow?? (again not my area of specialty)). This can cause other issues as well if you have something in a register (fresh from a calculation) &amp;nbsp;and something in memory as they are in different formats,&amp;nbsp;the one in the register is still in a native&amp;nbsp;64bit format where as the memory one will get widenned to 64 bits in order to be compared (as such they will not be equal)...&lt;/P&gt;
&lt;P&gt;Back to our first example .. you remember how it was missing the &lt;/P&gt;
&lt;P&gt;&lt;SPAN style="BACKGROUND-COLOR: yellow"&gt;L_000d: stloc.0 &lt;BR&gt;&lt;/SPAN&gt;&lt;SPAN style="BACKGROUND-COLOR: yellow"&gt;L_000e: ldloc.0&lt;/SPAN&gt; &lt;/P&gt;
&lt;P&gt;before the conversion to an integer? It is failing because it is using the 64 bit version of the float value (still in a register)&amp;nbsp;that has not yet been converted back to a 32 bit version.&lt;/P&gt;
&lt;P&gt;I took my best &lt;STRONG&gt;uneducated &lt;/STRONG&gt;guess, hopefully someone smarter than I can come through here and either confirm what I have said or identify the real problem :)&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;&lt;FONT color=#ff0000&gt;update: I finally found a resource on this and it seems I am in the right ballpark &lt;A href="http://blogs.msdn.com/davidnotario/archive/2005/08/08/449092.aspx"&gt;http://blogs.msdn.com/davidnotario/archive/2005/08/08/449092.aspx&lt;/A&gt;&lt;/FONT&gt;&lt;/P&gt;
&lt;P&gt;Another good question is, why is this doing anything at runtime :) Couldn't we multiply the two constants at compile&amp;nbsp;time?&lt;/P&gt;&lt;img src="http://geekswithblogs.net/gyoung/aggbug/80119.aspx" width="1" height="1" /&gt;</content>
        <wfw:comment>http://geekswithblogs.net/gyoung/comments/80119.aspx</wfw:comment>
        <slash:comments>4</slash:comments>
        <wfw:commentRss>http://geekswithblogs.net/gyoung/comments/commentRss/80119.aspx</wfw:commentRss>
        <trackback:ping>http://geekswithblogs.net/gyoung/services/trackbacks/80119.aspx</trackback:ping>
    </entry>
    <entry>
        <title>AOP with Generics Thoughts</title>
        <link rel="self" type="text/html" href="http://geekswithblogs.net/gyoung/archive/2006/05/29/80001.aspx" />
        <id>http://geekswithblogs.net/gyoung/archive/2006/05/29/80001.aspx</id>
        <published>2006-05-29T13:02:00-05:00:00</published>
        <updated>2006-05-29T22:08:00Z</updated>
        <content type="html">&lt;P&gt;As some of you may have realized, I am in the process of&amp;nbsp;re-implementing my AOP framework to fully support generics right now (figured I might as well as I am white boarding it for open source deployment anyways). I have come across numerous issues in dealing with generics. Today I sent an email to the castle project group (who are going through a similar task in supporting generics in Dynamic Proxy). I figured I would post that email here as well in case others have thoughts on some of the issues I present. &lt;/P&gt;
&lt;P&gt;
&lt;HR id=null&gt;

&lt;P&gt;&lt;/P&gt;&lt;SPAN style="FONT-SIZE: 9px; FONT-FAMILY: Arial"&gt;&lt;EM&gt;&lt;FONT size=3&gt;
&lt;DIV&gt;
&lt;DIV&gt;
&lt;DIV&gt;
&lt;DIV&gt;
&lt;DIV&gt;
&lt;DIV&gt;
&lt;DIV&gt;
&lt;DIV&gt;I am going to dump out some of my experiences here, I have already shared some of these with hammett off list but they may help in the design of the next version of dynamic proxy (and definitely bring up discussion points). &lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;The goal of truly supporting generics is the ability to reuse the generic proxy. This goal is not easily realized, I am beginning to question whether or not it is even worthwhile to create generic proxies.&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;Interceptors:&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;In order to have a functional generic dynamic proxy system I need to support generic aware point cuts.&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;Foo&amp;lt;T&amp;gt;.SomeMethod .. applies to all proxy instances&lt;/DIV&gt;
&lt;DIV&gt;Foo&amp;lt;SomeClass&amp;gt;.SomeMethod .. only applies to proxy instances where T=SomeClass&lt;/DIV&gt;
&lt;DIV&gt;Foo&amp;lt;T&amp;gt;.SomeMethod where T is ISomething .. dynamic application where T implements ISomething&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;This makes generation of generic proxies nasty at best. If we want to build a reusable proxy we have to build a superset of all defined behavior for any derived versions then conditionally not do anything at those interception points. We can move this behavior out to our interceptor cache ( i.e. simply pass a better context and return null representing no action to be taken) but this is still placing code into our proxies that we know for a fact will never be used.&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;ex:&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;an after interceptor defined only on Foo&amp;lt;int&amp;gt; must be placed on Foo&amp;lt;T&amp;gt; and&amp;nbsp;checked in an if&amp;nbsp;for all other classes .. This would allow us to reuse the generic proxy but has a trade off of performance for the other proxies. &lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;This problem becomes compounded when dealing with mixins as someone could define a mixin only to apply to Foo&amp;lt;SomeClass&amp;gt; and not to Foo&amp;lt;T&amp;gt;. As such our previous&amp;nbsp;solution of managing this in an interceptor cache&amp;nbsp;becomes invalid so we are forced to create separate proxies for closed types in many cases.&amp;nbsp;This will alleviate the problem of having garbage interceptor code but now we are also losing the ability to reuse our generic proxy.
&lt;SCRIPT&gt;&lt;!--
D(["mb","&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;This also adds a level of complexity to the cache. When given a Foo&amp;lt;SomeClass&amp;gt; you would first look in the cache for a Foo&amp;lt;SomeClass&amp;gt; .. if Foo&amp;lt;SomeClass&amp;gt; did not exist you would then have to analyze the metadata defining any aspects for Foo&amp;lt;SomeClass&amp;gt; to determine if you could use Foo&amp;lt;T&amp;gt; instead or whether you neded to generate a specific Foo&amp;lt;SomeClass&amp;gt; proxy. Providing we only ever _ADD_ behavior to a proxy we could reuse the open type proxies by inheriting from them for the more specific proxy having the inherited proxy adding further functionality to the base proxy ... This becomes interesting as for interceptors it may or may not add interception points meaning we have to inspect heavily the metadata in order to determine whether or not we actually need to create a subclass or whether we are simply receiving different interceptors at the same locations (easy operation but kind of annoying)\n&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;Of course to do things right you would want an operation that could also REMOVE an interception, example I want to add an interceptor to add on all List&amp;lt;T&amp;gt; except for List&amp;lt;MyUseVeryOftenClass&amp;gt; ... this operation obviously makes inheritance a bit more tricky.\n&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;Another issue I have come accross in dealign with generic mixins is the following situation.&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;public class A&amp;lt;T,V&amp;gt; {}&lt;/div&gt;\n&lt;div&gt;public interface B&amp;lt;T,V&amp;gt;{}&lt;/div&gt;\n&lt;div&gt;public class Bimplementor&amp;lt;T,V&amp;gt; {}&lt;/div&gt;\n&lt;div&gt;I want to mixin B with A though BImplementor .. when I go to generate my proxy there are two related issues.&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;1) Are T,V pointing to the same thing? :)&lt;/div&gt;\n&lt;div&gt;2) If not what should B\'s T,V be... I need some way of being given this metadata&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;they have defined .. (in some fictitous language that I will use through out this)&lt;/div&gt;\n&lt;div&gt;Class A&amp;lt;T,V&amp;gt; mixin B, BImplementor&amp;lt;A, B&amp;gt;&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;My proxy would need to be defined something similar to the following ..",1]
);

//--&gt;&lt;/SCRIPT&gt;
 &lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;This also&amp;nbsp;adds a&amp;nbsp;level of complexity to the cache. When given a Foo&amp;lt;SomeClass&amp;gt; you would first look in the cache for a Foo&amp;lt;SomeClass&amp;gt; .. if Foo&amp;lt;SomeClass&amp;gt; did not exist you would then have to analyze the metadata defining any aspects for Foo&amp;lt;SomeClass&amp;gt; to determine if you could use Foo&amp;lt;T&amp;gt; instead or whether you needed to generate a specific Foo&amp;lt;SomeClass&amp;gt; proxy. Providing we only ever _ADD_ behavior to a proxy we could reuse the open type proxies by inheriting from them for the more specific proxy having the inherited proxy adding further functionality to the base proxy ... This becomes interesting as for interceptors it may or may not add interception points meaning we have to inspect heavily the metadata in order to determine whether or not we actually need to create a subclass or whether we are simply receiving different interceptors at the same locations (easy operation but kind of annoying) &lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;Of course to do things right you would want an operation that could also REMOVE an interception, example I want to add an interceptor to add on all List&amp;lt;T&amp;gt; except for List&amp;lt;MyUseVeryOftenClass&amp;gt; ... this operation obviously makes inheritance a bit more tricky. &lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;Another issue&amp;nbsp;I have come across in dealing with generic mixins is the following situation.&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;public class A&amp;lt;T,V&amp;gt; {}&lt;/DIV&gt;
&lt;DIV&gt;public interface B&amp;lt;T,V&amp;gt;{}&lt;/DIV&gt;
&lt;DIV&gt;public class Bimplementor&amp;lt;T,V&amp;gt; {}&lt;/DIV&gt;
&lt;DIV&gt;I want to mixin B with A&amp;nbsp;though BImplementor .. when I go to generate my proxy there are two related issues.&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;1) Are T,V pointing to the same thing? :)&lt;/DIV&gt;
&lt;DIV&gt;2) If not what should B's T,V be... I need some way of being given this metadata&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;they have defined .. (in some fictitious language that I will use through out this)&lt;/DIV&gt;
&lt;DIV&gt;Class A&amp;lt;T,V&amp;gt; mixin B, BImplementor&amp;lt;A, B&amp;gt;&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;My proxy would need to be defined something similar to the following ..
&lt;SCRIPT&gt;&lt;!--
D(["mb","&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;public class AProxy &amp;lt;T,V,A,B&amp;gt; : B&amp;lt;A,B&amp;gt; {&lt;/div&gt;\n&lt;div&gt;}&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;because the T,V does not match up .. when I go to create an instance of this proxy I need to know what to put into A and B as they will not be provided. One could quite easily force a closed definition in the aspect definition \ni.e.&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;Class A&amp;lt;T,V&amp;gt; mixin B, BImplementor&amp;lt;int, double&amp;gt;&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;which would help many of these issues&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;The flip side of this is if we want them to match up (i.e. we want to reuse the same parameters of the original class)&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;public class AProxy&amp;lt;T,V&amp;gt; : B&amp;lt;T,V&amp;gt; {&lt;/div&gt;\n&lt;div&gt;}&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;perhaps an aspect definition similar to &lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;class A&amp;lt;T,V&amp;gt; mixin B, BImplementor&amp;lt;T,V&amp;gt; &lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;But there should also be a fair amount of error handling to insure that all values of T and V are in fact valid for A and B of the related interface&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;I guess the real point I am trying to make is that there are all sorts of fun conditions where we end up just using a closed proxy anyways .. How often will we really get to use an open proxy, are the times that we can use them worth all of the complexity? Similar behaviors could have been had in \n1.x by allowing inheritance within definitions (and inheriting proxies) but I have yet to see an implementation that did this .. ex:&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;Class A mixin B, BImplementor &lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;applies not only to A but all classes that inherit from A&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;In my particular case I have even further problems because I support multiple non-pure base class aggregation with a pattern similar to this &lt;a href\u003d\"http://www.codeproject.com/csharp/smip.asp\" target\u003d\"_blank\" onclick\u003d\"return top.js.OpenExtLink(window,event,this)\"&gt;http://www.codeproject.com&lt;WBR&gt;/csharp/smip.asp\n&lt;/a&gt;. The additional problem here is that while A&amp;lt;T&amp;gt; and B&amp;lt;T&amp;gt; may have no public fields (I therefor inherit from A&amp;lt;T&amp;gt;) .. I may run into a point where B&amp;lt;T&amp;gt; ends up having a public field later on (as such I would need to inherit from B&amp;lt;T&amp;gt; and aggregate A&amp;lt;T&amp;gt; in order to support the public fields)\n",1]
);

//--&gt;&lt;/SCRIPT&gt;
 &lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;public class AProxy &amp;lt;T,V,A,B&amp;gt; : B&amp;lt;A,B&amp;gt;&amp;nbsp;{&lt;/DIV&gt;
&lt;DIV&gt;}&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;because the T,V does not match up .. when I go to create an instance of this proxy I need to know what to put into A and B as they will not be provided. One could quite easily force a closed definition in&amp;nbsp;the aspect definition i.e.&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;Class A&amp;lt;T,V&amp;gt; mixin B, BImplementor&amp;lt;int, double&amp;gt;&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;which would help many of these issues&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;The flip side of this is if we want them to match up (i.e. we want to reuse the same parameters of the original class)&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;public class AProxy&amp;lt;T,V&amp;gt; : B&amp;lt;T,V&amp;gt; {&lt;/DIV&gt;
&lt;DIV&gt;}&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;perhaps an aspect definition similar to &lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;class A&amp;lt;T,V&amp;gt; mixin B, BImplementor&amp;lt;T,V&amp;gt; &lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;But there should also be a fair amount of error handling to insure that all values of T and V are in fact valid for A and B of the related interface&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;I guess the real point I am trying to make is that there are all sorts of fun conditions where we end up just using a closed proxy anyways .. How often will we really get to use an open proxy, are the times that we can use them worth all of the complexity? Similar behaviors could have been had in 1.x by allowing inheritance within definitions (and inheriting proxies) but I have yet to see an implementation that did this .. ex:&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;Class A mixin B, BImplementor &lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;applies not only to A but all classes that inherit from A&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;In my particular case I have even further problems because I support multiple non-pure base class aggregation with a pattern similar to this &lt;A onclick="return top.js.OpenExtLink(window,event,this)" href="http://www.codeproject.com/csharp/smip.asp" target=_blank&gt;http://www.codeproject.com&lt;WBR&gt;/csharp/smip.asp &lt;/A&gt;. The additional problem here is that while A&amp;lt;T&amp;gt; and B&amp;lt;T&amp;gt; may have no public fields (I therefor inherit from A&amp;lt;T&amp;gt;) .. I may run into a point where B&amp;lt;T&amp;gt; ends up having a public field later on (as such I would need to inherit from B&amp;lt;T&amp;gt; and aggregate A&amp;lt;T&amp;gt; in order to support the public fields)
&lt;SCRIPT&gt;&lt;!--
D(["mb","&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;Just some food for thought :)&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;Cheers,&lt;/div&gt;\n&lt;div&gt; &lt;/div&gt;\n&lt;div&gt;Greg &lt;/div&gt;&lt;/div&gt;",1]
);
D(["mb","&lt;div&gt;&lt;span class\u003dsg&gt;\n&lt;div&gt;&lt;br&gt;-- &lt;br&gt;If knowledge can create problems, it is not through ignorance that we can solve them. &lt;br&gt;&lt;br&gt;Isaac Asimov &lt;/div&gt;\n\n&lt;/span&gt;&lt;/div&gt;",0]
);
D(["ce"]);

//--&gt;&lt;/SCRIPT&gt;
 &lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;Just some food for thought :)&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;Cheers,&lt;/DIV&gt;
&lt;DIV&gt;&amp;nbsp;&lt;/DIV&gt;
&lt;DIV&gt;Greg &lt;/DIV&gt;&lt;/DIV&gt;
&lt;DIV&gt;&lt;SPAN class=sg&gt;
&lt;DIV&gt;&lt;BR&gt;&lt;/DIV&gt;&lt;/SPAN&gt;&lt;/DIV&gt;&lt;SPAN class=sg&gt;&lt;/DIV&gt;&lt;/DIV&gt;&lt;/SPAN&gt;&lt;SPAN class=sg&gt;&lt;BR&gt;&lt;/DIV&gt;&lt;/DIV&gt;&lt;/SPAN&gt;&lt;/DIV&gt;&lt;/DIV&gt;&lt;/FONT&gt;&lt;/EM&gt;&lt;/SPAN&gt;&lt;img src="http://geekswithblogs.net/gyoung/aggbug/80001.aspx" width="1" height="1" /&gt;</content>
        <wfw:comment>http://geekswithblogs.net/gyoung/comments/80001.aspx</wfw:comment>
        <slash:comments>2</slash:comments>
        <wfw:commentRss>http://geekswithblogs.net/gyoung/comments/commentRss/80001.aspx</wfw:commentRss>
        <trackback:ping>http://geekswithblogs.net/gyoung/services/trackbacks/80001.aspx</trackback:ping>
    </entry>
    <entry>
        <title>ICollection and ICollection&lt;&gt;</title>
        <link rel="self" type="text/html" href="http://geekswithblogs.net/gyoung/archive/2006/05/09/77757.aspx" />
        <id>http://geekswithblogs.net/gyoung/archive/2006/05/09/77757.aspx</id>
        <published>2006-05-09T22:19:00-05:00:00</published>
        <updated>2006-05-29T13:40:00Z</updated>
        <content type="html">&lt;P&gt;Eralier I posted (and deleted) about the Queue&lt;T&gt; class not implementing ICollection&lt;T&gt; from some research this is by design.&lt;/P&gt;
&lt;P&gt;From: &lt;A href="http://msdn2.microsoft.com/en-US/library/92t2ye13.aspx"&gt;http://msdn2.microsoft.com/en-US/library/92t2ye13.aspx&lt;/A&gt;&lt;BR&gt;&lt;BR&gt;"Some collections that limit access to their elements, like the Queue class and the Stack class, directly implement the ICollection interface."&lt;BR&gt;&lt;BR&gt;If you look, the interfaces are also very different from each other in what they include. The generic one includes methods such as ... Add, Remove, and Clear which do not exist on the non-generic ICollection.&lt;BR&gt;&lt;BR&gt;So conclusion .. Queue is correct but I have to say that having the generic and non-generic ICollections that represent completely different things is a bit confusing at best :-/&lt;/P&gt;&lt;img src="http://geekswithblogs.net/gyoung/aggbug/77757.aspx" width="1" height="1" /&gt;</content>
        <wfw:comment>http://geekswithblogs.net/gyoung/comments/77757.aspx</wfw:comment>
        <slash:comments>2</slash:comments>
        <wfw:commentRss>http://geekswithblogs.net/gyoung/comments/commentRss/77757.aspx</wfw:commentRss>
        <trackback:ping>http://geekswithblogs.net/gyoung/services/trackbacks/77757.aspx</trackback:ping>
    </entry>
    <entry>
        <title>Sorting Performance .NET 2.0</title>
        <link rel="self" type="text/html" href="http://geekswithblogs.net/gyoung/archive/2006/05/28/79851.aspx" />
        <id>http://geekswithblogs.net/gyoung/archive/2006/05/28/79851.aspx</id>
        <published>2006-05-28T00:17:00-05:00:00</published>
        <updated>2006-05-29T13:17:00Z</updated>
        <content type="html">&lt;P&gt;Be very careful when using Array.Sort in 2.0. I had posted a bug report about this a while ago &lt;A href="http://lab.msdn.microsoft.com/productfeedback/viewfeedback.aspx?feedbackid=62029e14-2d0b-4250-a163-1583034db250"&gt;http://lab.msdn.microsoft.com/productfeedback/viewfeedback.aspx?feedbackid=62029e14-2d0b-4250-a163-1583034db250&lt;/A&gt;&lt;/P&gt;
&lt;P&gt;The behavior observed was originally in arraylist (which uses Array.Sort internally) so keep in mind that this applies to it as well.&lt;/P&gt;
&lt;P&gt;Array.Sort(Items, 0, Items.Length, Comparer.Default); //takes 1 minute&lt;BR&gt;Array.Sort(Items2, 0, Items.Length, null); //takes 250 ms&lt;/P&gt;
&lt;P&gt;Items and Items2 are both clones of the same object []&lt;/P&gt;
&lt;P&gt;What is tricky about this code is that the second call does not actually call Array.Sort .. it calls Array&amp;lt;object&amp;gt; .Sort &lt;/P&gt;
&lt;P&gt;&lt;STRONG&gt;First call:&lt;/STRONG&gt;&lt;/P&gt;
&lt;P&gt;IL_0083: ldsfld class [mscorlib]System.Collections.Comparer [mscorlib]System.Collections.Comparer::Default&lt;BR&gt;IL_0088: call void [mscorlib]System.Array::Sort(class [mscorlib]System.Array, int32, int32, class [mscorlib]System.Collections.IComparer)&lt;/P&gt;
&lt;P&gt;&lt;STRONG&gt;Second Call:&lt;/STRONG&gt;&lt;/P&gt;
&lt;P&gt;IL_00c9: ldnull&lt;BR&gt;IL_00ca: call void [mscorlib]System.Array::Sort (!!0[], int32, int32, class [mscorlib]System.Collections.Generic.IComparer`1&lt;!!0&gt;)&lt;BR&gt;&lt;/P&gt;
&lt;P&gt;Ah .. :)&lt;/P&gt;
&lt;P&gt;Basically what the issue is is that there are 2 distinct sorting algorithms .. one that is Array.Sort one that is Array&lt;T&gt;.Sort .. they do &lt;STRONG&gt;not&lt;/STRONG&gt; use the same algorithm. From what I understand some changes were made in how pivots are chosen. &lt;/P&gt;
&lt;P&gt;&lt;/P&gt;
&lt;P&gt;&lt;/P&gt;&lt;/OBJECT&gt;
&lt;P&gt;&lt;/P&gt;&lt;img src="http://geekswithblogs.net/gyoung/aggbug/79851.aspx" width="1" height="1" /&gt;</content>
        <wfw:comment>http://geekswithblogs.net/gyoung/comments/79851.aspx</wfw:comment>
     