Have language features changed the way we work for the better?

Craig Murphy dropped a little coding challenge on his blog the other day. This prompted me to write the responses as below. I’ve tried to target each one towards using a particular technology as the framework has developed. Have a look and tell me which is your preferred answer, or propose a new one (but again try to target a language feature). I’d love to know who you why you choose that language feature over another. Option 1. With Linq private const string alphabet = "abcdefghijklmnopqrstuvwxyz";   static void Main(string[] args) { char c = Console.ReadKey().KeyChar;   var myChars = from character in alphabet where character <= c select character;   var fullRow = myChars.Skip(1).Reverse().Concat(myChars);   var myRows = (from character in myChars select ConvertToSpaces(character, fullRow));   var reverseRows = myRows.Reverse().Skip(1); myRows = myRows.Concat(reverseRows);   Console.WriteLine(Environment.NewLine);//Skip the ReadKey line foreach (string line in myRows) Console.WriteLine(line);   Console.ReadKey(); }   private static string ConvertToSpaces(char wanted, IEnumerable<char> characters) { return new string( (from character in characters select character == wanted ? character : ' ').ToArray()); } Option 2. With Generics   class Program { private const string alphabet = "abcdefghijklmnopqrstuvwxyz";   static void Main(string[] args) { char c = Console.ReadKey().KeyChar;   List<char> myChars = new List<char>(); foreach (char character in alphabet) { if (character <= c) myChars.Add(character); }   List<char> temp = new List<char>(Reverse<char>(AllButFirst<char>(myChars))); temp.AddRange(myChars); string fullRow = new string(temp.ToArray());   List<string> myRows = new List<string>(); foreach (char character in myChars) { myRows.Add(ConvertToSpaces(character, fullRow)); }   IEnumerable<string> reverseRows = AllButFirst<string>(Reverse<string>(myRows)); myRows.AddRange(reverseRows);   Console.WriteLine(Environment.NewLine);//Skip the ReadKey line foreach (string line in myRows) Console.WriteLine(line);   Console.ReadKey(); }   private static IEnumerable<T> Reverse<T>(IEnumerable<T> myChars) { Stack<T> reverse = new Stack<T>(); foreach (T character in myChars) { reverse.Push(character); } while (reverse.Count > 0) { yield return reverse.Pop(); } }   private static IEnumerable<T> AllButFirst<T>(IEnumerable<T> myChars) { bool first = true; foreach (T character in myChars) { if (first) first = false; else yield return character; } }   private static string ConvertToSpaces(char wanted, IEnumerable<char> characters) { StringBuilder result = new StringBuilder(); foreach (char character in characters) { result.Append(character == wanted ? character : ' '); } return result.ToString(); } } Option 3. Using IEnumerable   class ProgramDNv2 { private const string alphabet = "abcdefghijklmnopqrstuvwxyz"; static void Main(string[] args) { DiamondChars diamond = new DiamondChars(); diamond.chars = GetChars( Console.ReadKey().KeyChar); foreach (string line in diamond) { Console.WriteLine(line); } Console.ReadKey(); }   private static string GetChars(char MidChar) { string chars = alphabet.Substring(0, alphabet.IndexOf(MidChar) + 1); return chars; }   private class DiamondChars : IEnumerable<String> { public string chars;   #region IEnumerable<string> Members   public IEnumerator<string> GetEnumerator() { int index = 0; foreach (char character in chars) { yield return MakeLine(character, index); index++; } index--; foreach (char character in chars.Reverse()) { if (index < chars.Length - 1) { yield return MakeLine(character, index); } index--; } }   #endregion   private string MakeLine(char character, int index) { string line = new string(chars[index], 1).PadLeft(chars.Length - index);   if (index > 0) return line + new string(chars[index], 1).PadLeft(index * 2); else return line; }   #region IEnumerable Members   System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator() { return GetEnumerator(); }   #endregion }   } Option 4. Simple recursion   class ProgramDNv1 { static void Main(string[] args) { string input = "abcde"; StringBuilder result = new StringBuilder(); BuildDiamond(0, input, result); Console.WriteLine(result); }       private static void BuildDiamond(int index, string input, StringBuilder result) { string line = new string(input[index], 1).PadLeft(input.Length - index); string line2 = new string(input[index], 1).PadLeft(index * 2); result.Append(line); if (index > 0) result.Append(line2); result.Append(Environment.NewLine); if (index < input.Length - 1) { BuildDiamond(index + 1, input, result); result.Append(line); if (index > 0) result.Append(line2); result.Append(Environment.NewLine); } } } Now add a quick comment below telling you preferred implementation and briefly why. Thanks.

DotNet 3.5 or 2.0: Ajax

Originally AJAX (Atlas) was developed as a CTP and released as v1.0.61025. It got its official first release and now comes as 3.5.0.0. Lots of things break when assembly references are wrong, particularly in the web.config file. This error is but one particularly annoying symptom, as its un-catchable. An Error has occured System.Web.HttpParseException: The base class includes the field 'manager', but its type (System.Web.UI.ScriptManager) is not compatible with the type of control (System.Web.UI.ScriptManager).    at System.Web.Compilation.BaseTemplateCodeDomTreeGenerator.BuildFieldDeclaration(ControlBuilder builder)    at System.Web.Compilation.BaseTemplateCodeDomTreeGenerator.BuildSourceDataTreeFromBuilder(ControlBuilder builder, Boolean fInTemplate, Boolean topLevelControlInTemplate, PropertyEntry pse)    at System.Web.Compilation.BaseTemplateCodeDomTreeGenerator.BuildSourceDataTreeFromBuilder(ControlBuilder builder, Boolean fInTemplate, Boolean topLevelControlInTemplate, PropertyEntry pse)    at System.Web.Compilation.TemplateControlCodeDomTreeGenerator.BuildMiscClassMembers()    at System.Web.Compilation.PageCodeDomTreeGenerator.BuildMiscClassMembers()    at System.Web.Compilation.BaseCodeDomTreeGenerator.BuildSourceDataTree()    at System.Web.Compilation.BaseTemplateBuildProvider.GenerateCode(AssemblyBuilder assemblyBuilder)    at System.Web.Compilation.AssemblyBuilder.AddBuildProvider(BuildProvider buildProvider)