Another example of using C# 4 dynamic typing


Here’s a good example of where using Dynamic is handy. Imagine I want to write an all-purpose Excel reader in .NET. This reader class should be able to take in a filename and return me an object which I can use to get data out of the spreadsheet. In itself, that’s not overly difficult using e.g. OLE DB to read from the spreadsheet, but there’s always some boiler-plate involved in creating a .net object to hold the result of the query (unless you want to use DataTables throughout your application), which means you have to create a class to hold the result, and a translator of some sort to go from a DataTable to that object.

Enter the DynamicDataRow object. This handy object sits on top of a standard DataRow but allows dynamic property (column) access at runtime. You can consume it very easily: –

image

Obviously, we know that the shape of the data will change depending on the spreadsheet content – but don’t want the actual ExcelReader code to change with different spreadsheets.

The ExcelReader.LoadDocument code itself is very plain – it just does some simple OLE DB connection work to read the data into a bog-standard DataSet, and then returns an ExcelDocument object which takes in the DataTable containing the spreadsheet data and populates the Rows property with a DynamicDataRow object for each row in the Table. Notice that so far I’ve not discussed anything C#4 specific yet – just plain OLE DB and some properties setters etc.

In fact, the only bit of C#4 is what we enumerate over i.e. where I have “dynamic row in document.Rows”. In this case, “row” is an object of type DynamicDataRow. This is a simple class which wraps around a normal DataRow but allows direct access to properties instead of the somewhat ugly column indexer notation that you get with a DataRow: –

image

It’s a tiny class. All it does is inherit from DynamicObject and override the TryGetMember method to remove the need for indexer accessors and replace them with property accessors, so instead of row[“MyColumn”] you can now just do row.MyColumn. Again, though, from a client point of view, this is very easy to consume – look at the first code sample and realise that that will work for any spreadsheet whatsoever. Also notice how we treat “row” as dynamic, rather than DynamicDataRow (or object), as we want the property accessors to get intercepted by the TryGetMember method…
Advertisements

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s