Essential C# 6 Features You Need to Know!

With the final version of C# 6 having been released, we can seen that a lot of syntax changes have occurred since its inception. Because of this, I’ve noticed that most of the blog posts currently on the internet don’t work anymore or are too vague about how they implemented a feature.

I thought it would be useful to make a list of the most essential C# 6 features with simple code examples that would make it both easy to understand and simple to copy/paste a sample into a new console app to try it. Let’s jump in.

The complete Visual Studio 2015 Console Application with all of the demos shown in this article can be found on Github.

Static Using Syntax

In previous versions of C#, if we wanted to print something to the Console, we would write the following line of code:

using System;

namespace CSharpSix
{
    class Program
    {
        static void Main(string[] args)
        {
            Console.WriteLine("Hello World!");
        }
    }
}

With C# 6, you can now add the using static qualifier and reference the WriteLine method by itself as shown below:

using static System.Console;

namespace CSharpSix
{
    class Program
    {
        static void Main(string[] args)
        {
            WriteLine("Hello World!");
        }
    }
}

This also works for classes that we’ve created ourselves. Take a look at the following example.

using static System.Console;
using static CSharpSix.YetAnotherClass;

namespace CSharpSix
{
    class Program
    {
        static void Main(string[] args)
        {
            WriteLine("Hello World!");
            HelloBack();
        }
    }
    static class YetAnotherClass
    {
        public static void HelloBack()
        {
            WriteLine("Hello Computer!");
        }
    }
}

Since we declared YetAnotherClass with the static keyword, we can run the method by just calling the method name. The output for this sample would be :

Hello World!
Hello Computer!

Auto-Property Initializers

In the past, we may have created our properties with a getter and setter and initialized our constructor with the value as shown below.

using System;

namespace CSharpSix
{
    class Program
    {
        static void Main(string[] args)
        {
            Customer cust = new Customer();
            Console.WriteLine(cust.customerID);
            Console.ReadLine();
        }
    }

    public class Customer
    {
        public Customer()
        {
            customerID = Guid.NewGuid();
        }

        public Guid customerID { get; set; }
    }

}

We can now modify the Customer class and populate the property called customerID with inline initialization in C# 6.

using System;
using static System.Console;

namespace CSharpSix
{
    class Program
    {
        static void Main(string[] args)
        {
            Customer cust = new Customer();
            WriteLine(cust.customerID);
            ReadLine();
        }
    }

    public class Customer
    {
        public Guid customerID { get; set; } = Guid.NewGuid();
    }

}

The output for this sample will be a random guid generated by the system.

Dictionary Initializers

In C# 5, you would initialize the Dictionary with a {"Key", "Value"} syntax, as in the example below.

using System.Collections.Generic;

namespace CSharpSix
{
    class Program
    {
        static void Main(string[] args)
        {
            var stars = new Dictionary<string, string> ()
            {
                 { "Michael Jordon", "Basketball" },
                 { "Peyton Manning", "Football" },
                 { "Babe Ruth", "Baseball" }
            };

            foreach (KeyValuePair<string, string> keyValuePair in stars)
            {
                Console.WriteLine(keyValuePair.Key + ": " +
                keyValuePair.Value + "\n");
            }

            Console.ReadLine();
        }
    }
}

In C# 6, you just place the key between two square brackets ["Key"] and then set the value of the key ["Key"] = "value". This syntax is cleaner, in my opinion, and reduces the amount of errors that the old way produced.

using System.Collections.Generic;
using static System.Console;

namespace CSharpSix
{
    class Program
    {
        static void Main(string[] args)
        {
            var stars = new Dictionary<string, string> ()
            {
                ["Michael Jordan"] = "Basketball",
                ["Peyton Manning"] = "Football",
                ["Babe Ruth"] = "Baseball"
            };

            foreach (KeyValuePair<string, string> keyValuePair in stars)
            {
                WriteLine(keyValuePair.Key + ": " +
                keyValuePair.Value + "\n");
            }

            ReadLine();
        }
    }
}

String Interpolation

Prior to C# 6.0, we typically concatenated two or more strings together with one of the following methods:

using System;

namespace CSharpSix
{
    class Program
    {
        static void Main(string[] args)
        {
            string firstName = "Michael";
            string lastName = "Crump";

            Console.WriteLine("Name : " + firstName + " " + lastName);
            Console.WriteLine("Name : {0} {1}", firstName, lastName);

            Console.ReadLine();
        }
    }
}

In C# 6.0, we have a cleaner way to format a string by writing our own arguments instead of referring to them as placeholders. Just make sure you use the $ before the start of the string.

using static System.Console;

namespace CSharpSix
{
    class Program
    {
        static void Main(string[] args)
        {
            string firstName = "Michael";
            string lastName = "Crump";

            WriteLine($"{firstName} {lastName} is my name!");

            ReadLine();
        }
    }
}

The output for this example is :

Michael Crump is my name!

nameOf Expression

This feature was designed due to the large amounts of code that many enterprise level applications have. One common error is using hard-coded name strings with an error message. Due to the nature of the apps in general and re-factoring, sometimes the names change and the string representation is left alone – thus breaking the app. Here is one example.

using System;
using static System.Console;


namespace CSharpSix
{
    class Program
    {
        static void Main(string[] args)
        {

            DoSomething("Hi");
            ReadLine();
        }

        public static void DoSomething(string name)
        {
            if (name == null) throw new Exception("Name is null");
        }
    }
}

This code will not produce an error as expected as the string is equal to null.

What happens if someone changes the name variable to newName? Since we hard-coded the “Name is null” error, that is what will appear to the end-user. We would rather it now say, “newName is null”, but the compiler cannot recognize this mistake.

In C# 6.0, we can refactor our code to remove the string literals and use the nameof expression.

using System;
using static System.Console;


namespace CSharpSix
{
    class Program
    {
        static void Main(string[] args)
        {

            DoSomething("Hi");
            ReadLine();
        }

        public static void DoSomething(string newName)
        {
            if (newName == null) throw new Exception(nameof(newName) + " is null");
        }
    }
}

This results in cleaner code and type safety when retrieving member names. In this case, if we removed the newName variable and gave it a new name then the compiler would catch the error before the program was executed.

Expression Bodied Function & Property

Functions and properties in lambda expressions save you from defining your function and property statement block. Take note of the MultipleNumbers function below:

using static System.Console;

namespace CSharpSix
{
    class Program
    {
        private static double MultiplyNumbers(double num1, double num2) => num1 * num2;

        static void Main(string[] args)
        {
            double num1 = 5;
            double num2 = 10;

            WriteLine(MultiplyNumbers(num1, num2));
            ReadLine();
        }
    }
}

The result of the above program would be 50.

This shorthand notation may be confusing at first, but I think after you get used to it then can make your program much more readable.

Exception Filters

Exception filters have been supported in Visual Basic, but are new to the C# compiler. They allow you to specify a condition for a catch block. We typically used the following in C# 5:

using System;
using static System.Console;


namespace CSharpSix
{
    class Program
    {
        static void Main(string[] args)
        {
            var httpStatusCode = 404;
            Write("HTTP Error: ");

            try
            {
                throw new Exception(httpStatusCode.ToString());
            }
            catch (Exception ex)
            {
                if (ex.Message.Equals("500"))
                    Write("Bad Request");
                else if (ex.Message.Equals("401"))
                    Write("Unauthorized");
                else if (ex.Message.Equals("402"))
                    Write("Payment Required");
                else if (ex.Message.Equals("403"))
                    Write("Forbidden");
                else if (ex.Message.Equals("404"))
                    Write("Not Found");
            }

            ReadLine();
        }
    }
}

Rather than entering the catch block and checking to see which condition met our exception, we can now decide if we even want to enter the specific catch block.

using System;
using static System.Console;


namespace CSharpSix
{
    class Program
    {
        static void Main(string[] args)
        {
            var httpStatusCode = 404;
            Write("HTTP Error: ");

            try
            {
                throw new Exception(httpStatusCode.ToString());
            }
            catch (Exception ex) when (ex.Message.Equals("400"))
            {
                Write("Bad Request");
                ReadLine();
            }
            catch (Exception ex) when (ex.Message.Equals("401"))
            {
                Write("Unauthorized");
                ReadLine();
            }
            catch (Exception ex) when (ex.Message.Equals("402"))
            {
                Write("Payment Required");
                ReadLine();
            }
            catch (Exception ex) when (ex.Message.Equals("403"))
            {
                Write("Forbidden");
                ReadLine();
            }
            catch (Exception ex) when (ex.Message.Equals("404"))
            {
                Write("Not Found");
                ReadLine();
            }

            ReadLine();
        }
    }
}

Await in a Catch and Finally Block

Brand new to C# 6, you can write asynchronous code inside in a catch/finally block. This will help developers as they often need to log exceptions to a file or database without blocking the current thread. Here is an example of how one would work:

using System;
using System.Net.Http;
using System.Threading.Tasks;
using static System.Console;


namespace CSharpSix
{
    class Program
    {
        static void Main(string[] args)
        {
            Task.Factory.StartNew(() => GetPage());
            ReadLine();
        }

        private async static Task GetPage()
        {
            HttpClient client = new HttpClient();
            try
            {
                var result = await client.GetStringAsync("http://www.telerik.com");
                WriteLine(result);
            }
            catch (Exception exception)
            {
                try
                {
                    //This asynchronous request will run if the first request failed. 
                    var result = await client.GetStringAsync("http://www.progress.com");
                    WriteLine(result);
                }
                catch
                {
                    WriteLine("Entered Catch Block");
                }
                finally
                {
                    WriteLine("Entered Finally Block");
                }
            }
        }
    }
}

Null Conditional Operator

Every developer hates NullReferenceException errors! This is the typical code one would check prior to C# 6.0.

using System;
using static System.Console;


namespace CSharpSix
{
    class Program
    {
        static void Main(string[] args)
        {
            Person person = new Person();
            if (person.Name == String.Empty)
            {
                person = null;
            }

            WriteLine(person != null ? person.Name : "Field is null.");

            ReadLine();
        }
    }

    public class Person
    {
        public string Name { get; set; } = "";
    }
}

This returns “Field is null”. If we enter some data into name, then the console prints out whatever is contained in the name.

Using C# 6.0, we can use ?. to check if an instance is null or not. The code listing below will print the person.Name field if one is supplied or will print “Field is null” if one isn’t supplied.

using System;
using static System.Console;


namespace CSharpSix
{
    class Program
    {
        static void Main(string[] args)
        {
            Person person = new Person();
            if (person.Name == String.Empty)
            {
                person = null;
            }

            WriteLine(person?.Name ?? "Field is null.");

            ReadLine();
        }
    }

    public class Person
    {
        public string Name { get; set; } = "";
    }
}

Wrap-Up

Thankfully C# 6.0 is final and can be used in production environments now. I wasn’t able to touch on every feature, but you can always reference MSDN for more info.

I would also encourage you to check out what is included in Visual Studio 2015 while you are there. In case you are wondering, all of our UI components included in DevCraft are fully functional with Visual Studio 2015 and hopefully you can use some of the cool new C# 6 features that I wrote about today.

So did I miss a cool feature or do you have a better way to do something? Sounds off in the comments below!

Comments

  • Pingback: Dew Drop – October 5, 2015 (#2104) | Morning Dew()

  • Nice run-through! Thanks!

  • Roman Dvoskin

    Good summary. I think “Async in a Catch and Finally Block” should read “Await in a Catch and Finally Block” and there should be an example of an “await” in the catch or finally block.

    • I agree completely. I’ve updated the text and included an example. Thanks for making this post better!

    • I agree completely. I’ve updated the text and included an example. Thanks for making this post better!

  • n0tch

    Hi, really helpful summary, thanks. I think there is a tiny issue on the Null Condition Operator section, if the person had a name, wouldn’t it write that name to the console and not “Field is not null”?

    • Yes it would! Thanks for letting me know. The post has been updated.

  • Cesar Mello

    Nice article, thank you!!! Best regards. Mello

  • TheRatiocinator

    I enjoyed this article, and some of these features sound very useful and “cleanifying”. Did they add anything to spellcheck the names of incredibly famous basketball players? 🙂

    • heh, it is fixed now. Thanks for pointing it out! 🙂

  • seanhunt

    Well, Microsoft must sell a product, but this stuff does not impress me in the slightest

    • mxmissile

      exactly what are they selling by giving us these C# conveniences?

      • seanhunt

        An update… that they can sell that provides me little benefit. Mostly these are syntactic shortcuts which tend to hurt maintainability. Not all of them. but most. Hey, C# is a great tool. It’s hard to improve at this point, so Microsoft has to reach to find anything it can add to claim it has a new product you should buy.
        Dictionary Initializers, String Interpolation, exception filters, Static Syntax… all trivial.
        Await in catch/finally block and null conditional operator are nice, but big hoopty doo
        None of them compare to generics, LINQ, MVC, TPL and Concurrent Objects.
        These updates are mostly trivial and some are of quite debatable benefit, but hey, we now have .Net 6

        • I don’t disagree to your comments in general, but the ?. operator is the greatest thing since sliced bread. Now you can chain object access without having to break each one down and check for null explicitly.

          Instead of writing
          if ( MyObject != null )
          if (MyObject.MyEncapsulatedObject != null )
          MyObject.MyEncapsulatedObject.DoSomething();

          you can now write
          MyObject?.MyEncapsulatedObject?.DoSomething()

          ?. stops evaluation and returns null if a null object reference is encountered.

          • seanhunt

            That’s why I mentioned it in the nice column. Actually, that’s probably the best one, but I won’t be using it. I’ve been burned before. I don’t risk anything being null. I don’t test for it. I don’t allow it.

  • Mark Johnson

    Those Curly brackets sure look square to me.

  • Richard

    “throw new Exception(“Name is null”);”

    I wish Microsoft had made the System.Exception class abstract to stop people doing this.

    There are dozens of specific exceptions you could throw – in this case, an ArgumentNullException would be appropriate. If you can’t find one that meets your needs, you can create your own.

    Throwing a new System.Exception is just lazy, and makes your code harder to call.

    • Keep in mind that this is just sample code intended to show the developer what happened with an explicit error message.

      • Richard

        Because nobody ever copies sample code into a live application without understanding it, right? 🙂

  • syclee

    Thanks for the article, enjoyed reading it. One slight gripe is the ‘nameof’ section could be improved. I think the example could be better if the first example used variable ‘name’, and second example used variable ‘newName’ (instead of ‘newName’ and ‘city’).

    • I changed it all because of you. 🙂

      • It still mentions “the city variable”.

        • Kailash Vaishnav

          Even it’s same its doesn’t matter. It’s variable name only. It should be same in both example.

          • I wasn’t talking to you. And your English and your comprehension suck.

          • Kailash Vaishnav

            Check first you English, In your comment you have mention that “the city variable”. In this First letter should be capital like “The city variable”

  • This was fixed earlier. Make sure you clear your browser cache. Happy coding!

    • spaolo

      Very good! I was worried MJ would sue you 🙂

  • Kailash Vaishnav

    Thanks Michal for given short intro about C#6

  • Pingback: Automate the Planet()

  • marius delport

    Hi i’ve seen this type of programming in my live in a early stage with (Bro…..) it make a lot of sence. Good stuf go on.

  • Radha Reddy

    Thank u

  • Ammar Hassan

    Great stuff. thanks for sharing.

  • Pingback: Microsoft //Build 2016 | Software Development in a Nutshell()