4 Features for C# 4.0

Plenty of powerful new language features have fairly recently become mainstream with the launch of VS 2008 in Nov 2007 that supports C# 3.0, amongst which:

  • Implicitly Typed Local Variables
  • Extension Methods
  • Lambda Expressions
  • Object and Collection Initializers
  • Anonymous Types
  • Query Expressions
  • Automatically Implemented Properties

Although most of us are still trying to fully absorb the above features, there has been some speculation going on about what sort of features we would like to see in the next version of C# and Jeremy Miller has posted a question with what he would like to see.

Here are some of the language features I would really like to see in C#:

1. Implementing Interfaces by delegation to fields

I would like to see support in C# 4.0 that would allow us to delegate the implementation of an interface to a field in the implementing class. For example this could look something like the following:

    //faux code
    public class Foo : IList<string>
    {
        private List<string> _Collection implements IList<string>;

        public Foo()
        {
            _Collection = new List<string>();
        }
    }

The field could be delegated to implement one or more interfaces from the encapsulating class by separating them with a comma. This would remove a lot of redundant code in scenarios like the above one, ie. Instead of implementing a lot of pass through functions on the encapsulating class (Foo) the functions are directly mapped to the delegated interface implementation. This sort of functionality would also enhance support for mixins  

This is known as the delegation pattern and from wikipedia:

The delegation pattern is a technique where an object outwardly expresses certain behaviour but in reality delegates responsibility for implementing that behaviour to an associated object in an Inversion of Responsibility. The delegation pattern is the fundamental abstraction that underpins composition (also referred to as aggregation), mixins and aspects.

Taking it one step even further, one could override the delegated implementation in a syntax like so:

    public class Foo : IList<string>
    {
        private List<string> _Collection { get; set; } implements IList<string>;

        public Foo()
        {
            _Collection = new List<string>();
        }

        //This would override the delegated implementation 
        // for nice mixin functionality and easy decorator pattern implementation
        public int IList.Add(string value)
        {
            if (!_Collection.Contains(value))
                _Collection.Add(value);
        }
    }

2. Anonymous type return values

I would like to see the anonymous types becoming first class 'citizens' in C#. Anonymous types can only be used in a local scope and cannot be returned from functions. It would be nice if we could return our strongly typed Linq Query Projection from a function eg:

        //faux code
        public var GetProductInfos()
        {
            var productInfos =
                from p in products
                select new { p.ProductName, p.Category, Price = p.UnitPrice };

            return productInfos;
        }

 

3. Some Duck-typing or Structural Subtyping support

If a class has a property or a method signature that is the same as the method signature on a declared interface, then that class implicitly implements that interface, if it is not already inheriting from it.   The class would implicitly implement an interface if and only if it would implement all the method signatures of a given interface. Basically

if it walks like a duck and it quacks like a duck, then I would call it a duck! (James Riley)

So what is the difference with Structural Subtyping? I would argue that structural subtyping is more suitable to the static style of C#, since it is a 'static duck typing', or according to wikipedia:

Duck typing differs from structural typing in that only the part of the structure accessed at run time is checked for compatibility.

Lets see how this could be beneficial through a use case:

The .Net framework has a few controls that implement a ReadOnly property amongst which are the TextBox, DataGrid, NumericUpDown.

Lets define the IReadOnlyRestrictable interface in our source like so:

        public interface IReadOnlyRestricable
        {
            bool ReadOnly { get; set; }
        }


Let's assume that we wanted to Loop through all the controls on a form and anything that satisfies the above interface signature (i.e has a property 'ReadOnly') set its readonly property to true. With ducktyping the qualifying controls would be cast to a valid IReadOnlyRestrictable instance like below, without needing to resort to reflection

        foreach (Control c in f.Controls)
        {
            //would like to have implicit cast to IReadOnlyRestrictable if interface contract is in class we are checking against
            IReadOnlyRestricable editable = c as IReadOnlyRestricable; 
            if (editable != null)
                editable.ReadOnly = true;
        }

The main advantage I see with ducktyping is that you can declare interfaces for libraries that you do not have access to, this can be useful in scenarios where you would like to minimise dependancies, check out Phil Haacks more extensive post on duck typing and why he believes it would benefit C# developers.

Apparantly, the c# foreach operator already uses duck typing according to Krzysztof Cwalina

 

4. Safe Null Dereferencing Operator

I would really like to see a safe way to dereference a null value in an expression that of form Object.Property.Property.Value.

For example if we had Customer?.FirstName and Customer was null, then the expression would evaluate to null instead of raising a null reference exception.
Some more examples of how this could work:

    //FAUX CODE
    //this would throw a null reference exception as usual if either Customer or Order was null
    int orderNumber = Customer.Order.OrderNumber;

    //this would not compile since it would require a nullable return type
    int orderNumber = Customer.Order?.OrderNumber;

    //this would return null if a Customer was null or if Order was null 
    int? orderNumber = Customer?.Order?.OrderNumber;
    if (orderNumber.HasValue) 
        //... do something with it

    //instead of having to do 
    if ((Customer != null) && (Customer.Order != null))
        int a = Customer.Order.OrderNumber

 

Wrap up

Here is a recent interview of the C# 4.0 team in the room where all the magic happens

What is your take? Do you agree? What features you would like to see?

Comments are closed