Hugoware

The product of a web developer with a little too much caffeine

Posts Tagged ‘Extension Methods

Null Instance Extension Methods

with 4 comments

Checking for null can be time consuming and add a lot of extra noise to the code you write. In some ways it can reduce the readability of your code and obscure the purpose of your functions.

For example, check out all of the null checks required for this bit of code.

public static int GetVersion() {
	
	//check if this exists
	if (!File.Exists(PATH_APP_DETAILS)) { return DEFAULT_VERSION; }

	//try and load the document
	XDocument document = null;
	try {
		document = XDocument.Load(PATH_APP_DETAILS);
	}
	catch {
		return DEFAULT_VERSION;
	}
	if (document == null) { return DEFAULT_VERSION; }
	
	//find the element
	XElement release = document.XPathSelectElement("app/release");
	if (release == null) { return DEFAULT_VERSION; }
	
	//get the value
	XAttribute version = release.Attribute("version");
	if (version == null) { return DEFAULT_VERSION; }
	
	//convert the version
	int current = int.TryParse(version.Value, out current) ? current : DEFAULT_VERSION;
	return current;
	
}

Yikes… that is a lot of code for such a small task but what else can you do? You can’t just call methods on something that is null or your app is going to blow up… or can you?

Null Instance Extension Methods

Extension methods feel magical the first time you see them in action but ultimately they are just static methods that can be invoked from anywhere in your project.

But here is the neat thing — Since an extension method isn’t tied to the instance of a class then they can be invoked without an instance of the class.

Sound confusing? Here is an example of what I mean…

//create an extension method
public static class StringExtensions {
	public static void Test(this string value) {
		Console.WriteLine("Hello from a null test!");
	}
}

//and then call it
string nothing = null;
nothing.Test(); //ok!
nothing.ToUpper(); //crash

You’ll notice that the call to Test worked fine – If you put a break point in the method and check the value argument then you’ll notice it is actually null! We were able to call the method Test even though there wasn’t an instance of a string.

So how can this help us? Well let’s take the same XML problem from earlier in the post and create some extension methods that don’t care if the instance being invoked is null or not.

//helper extension methods for XML documents
public static class XmlExtensions {
	
	//loads an xml document to use
	public static XDocument LoadDocument(this XDocument document, string path) {
		if (!File.Exists(path)) { return null; }
		try { return XDocument.Load(path); }
		catch { return null; }
	}
	
	//uses an XPath to find an element
	public static XElement GetElement(this XDocument document, string path) {
		return document is XDocument ? document.XPathSelectElement(path) : null;
	}
	
	//returns the value of an attribute
	public static string GetAttribute(this XElement element, string name) {
		XAttribute attribute = element is XElement ? element.Attribute(name) : null;
		return attribute is XAttribute ? attribute.Value : string.Empty;
	}
}

Now let’s take a look at how we can solve the same problem as before but with these new extension methods…

public static int GetVersion() {
	
	//open the document (Mono)
	XDocument document = document.LoadDocument(PATH_APP_DETAILS);

	//It appears you have to do it like this in Visual Studio
	//XDocument document = ((XDocument)null).LoadDocument(PATH_APP_DETAILS);
	
	//find the element
	XElement release = document.GetElement("app/release");
	
	//get the version
	string version = release.GetAttribute("version");
	
	//convert and return the value
	int current = int.TryParse(version, out current) ? current : DEFAULT_VERSION;
	return current;
}

As far as I can tell, no matter what you throw at this code, you will either get the default version or the value in the XML document. This definitely reduces the lines of code count… but the clarity gains might be debatable.

  1. A developer modifying this code might not realize the value could be null or could be a real object. If they call an instance method and the value ends up being null then the application is going to crash.
  2. Some developers are going to scratch their heads when they read the line XDocument document = document.LoadDocument(...). Invoking a method on a value you’re declaring and should be null and returning the result it to itself? Huh?
  3. The more forgiving your code is then the more prone to external errors it will be, which in turn will introduce subtle runtime errors in your applications. Sometimes it’s a better idea just to throw an exception and keep the program from running.

So, while this approach has benefits it also has pitfalls. Make sure to evaluate the risks before using something like this in your code. If implemented carefully this could reduce complexity in your application…

…or at least make for a neat parlor trick the next time you’re with your dev team.

Advertisements

Written by hugoware

August 22, 2010 at 9:14 pm

Enumeration Extensions 2.0

with 8 comments

A while back I had posted some code about making it easier to work with enumerated types — Especially with the Flags attribute. An experienced programmer won’t have a hard time understanding all the voodoo magic behind the the bitwise operators but for the rest of us then something a little easier to read is always welcome.

The problem with the previous code is that it was created to work with the project I was currently working on so I didn’t put a lot of effort into making it work with multiple types. That said, below is the official version 2.0 of the EnumerationExtensions class.

using System;

namespace Extensions {

    /// <summary>
    /// Extension methods to make working with Enum values easier
    /// </summary>
    public static class EnumerationExtensions {

        #region Extension Methods

        /// <summary>
        /// Includes an enumerated type and returns the new value
        /// </summary>
        public static T Include<T>(this Enum value, T append) {
            Type type = value.GetType();

            //determine the values
            object result = value;
            _Value parsed = new _Value(append, type);
            if (parsed.Signed is long) {
                result = Convert.ToInt64(value) | (long)parsed.Signed;
            }
            else if (parsed.Unsigned is ulong) {
                result = Convert.ToUInt64(value) | (ulong)parsed.Unsigned;
            }

            //return the final value
            return (T)Enum.Parse(type, result.ToString());
        }

        /// <summary>
        /// Removes an enumerated type and returns the new value
        /// </summary>
        public static T Remove<T>(this Enum value, T remove) {
            Type type = value.GetType();

            //determine the values
            object result = value;
            _Value parsed = new _Value(remove, type);
            if (parsed.Signed is long) {
                result = Convert.ToInt64(value) & ~(long)parsed.Signed;
            }
            else if (parsed.Unsigned is ulong) {
                result = Convert.ToUInt64(value) & ~(ulong)parsed.Unsigned;
            }

            //return the final value
            return (T)Enum.Parse(type, result.ToString());
        }

        /// <summary>
        /// Checks if an enumerated type contains a value
        /// </summary>
        public static bool Has<T>(this Enum value, T check) {
            Type type = value.GetType();

            //determine the values
            object result = value;
            _Value parsed = new _Value(check, type);
            if (parsed.Signed is long) {
                return (Convert.ToInt64(value)& (long)parsed.Signed) == (long)parsed.Signed;
            }
            else if (parsed.Unsigned is ulong) {
                return (Convert.ToUInt64(value) & (ulong)parsed.Unsigned) == (ulong)parsed.Unsigned;
            }
            else {
                return false;
            }
        }

        /// <summary>
        /// Checks if an enumerated type is missing a value
        /// </summary>
        public static bool Missing<T>(this Enum obj, T value) {
            return !EnumerationExtensions.Has<T>(obj, value);
        }

        #endregion

        #region Helper Classes

        //class to simplfy narrowing values between 
        //a ulong and long since either value should
        //cover any lesser value
        private class _Value {

            //cached comparisons for tye to use
            private static Type _UInt64 = typeof(ulong);
            private static Type _UInt32 = typeof(long);

            public long? Signed;
            public ulong? Unsigned;

            public _Value(object value, Type type) {

                //make sure it is even an enum to work with
                if (!type.IsEnum) {
                    throw new ArgumentException("Value provided is not an enumerated type!");
                }

                //then check for the enumerated value
                Type compare = Enum.GetUnderlyingType(type);

                //if this is an unsigned long then the only
                //value that can hold it would be a ulong
                if (compare.Equals(_Value._UInt32) || compare.Equals(_Value._UInt64)) {
                    this.Unsigned = Convert.ToUInt64(value);
                }
                //otherwise, a long should cover anything else
                else {
                    this.Signed = Convert.ToInt64(value);
                }

            }

        }

        #endregion

    }

}

This code results in a much easier to read syntax and is mildly better at avoiding type casting issues. Instead of defaulting to int as the other version did, this version attempts to decide between Int64 or UInt64 since either could meet the requirements for any of their lesser counterparts.

Now we can use syntax similar like you see below…

//create the typical object
RegexOptions options = RegexOptions.None;

//Assign a value
options = options.Include(RegexOptions.IgnoreCase); //IgnoreCase

//Or assign multiple values
options = options.Include(RegexOptions.Multiline | RegexOptions.Singleline); //IgnoreCase, Multiline, Singleline

//Remove values from the list
options = options.Remove(RegexOptions.IgnoreCase); //Multiline, Singleline

//Check if a value even exists
bool multiline = options.Has(RegexOptions.Multiline); //true
bool ignoreCase = options.Missing(RegexOptions.IgnoreCase); //true

Anyways, a whole lot easier to read in my opinion. Enjoy!

Written by hugoware

February 23, 2010 at 10:26 pm

Build A Smarter Loop With C#

with 3 comments

One of the first things every programmer learns in how to loop through an array of information. We learn how to do for, foreach, while loops but then we never really improve on them. For the most part the standard loop is as far as a programmer goes.

It seems to me that loops should be more intelligent than that. In fact we often write code that uses the loop for additional information. It isn’t uncommon to see a loop check if it is an even or odd index or the first or last value.

Modestly Smarter Loops

I really like lambdas a lot – in fact probably, too much. Being able to pass an delegate around like an argument definitely can be abused but in some cases it can make for some really elegant code. Let’s look at some code that can improve working with arrays.

namespace LoopExtensions {
//Some comments removed for brevity...

    #region Extension Methods

    /// <summary>
    /// Handles looping through collections with additional details
    /// </summary>
    public static class LoopExtensionMethods {

        public static IEnumerable<T> Each<T>(this IEnumerable<T> collection, 
            Action<ElementDetail<T>> each) {
            return LoopExtensionMethods.Each<T>(collection, 0, collection.Count(), each);            
        }

        public static IEnumerable<T> Each<T>(this IEnumerable<T> collection, 
            int start, 
            Action<ElementDetail<T>> each) {
            return LoopExtensionMethods.Each<T>(collection, start, collection.Count(), each);
        }

        public static IEnumerable<T> Each<T>(this IEnumerable<T> collection,
            int start,
            int end,
            Action<ElementDetail<T>> each) {
            Action<ElementDetail<T>, T> handle = (detail, item) => { each(detail); };
            return LoopExtensionMethods.Each<T>(collection, start, end, handle);
        }

        public static IEnumerable<T> Each<T>(this IEnumerable<T> collection, 
            Action<ElementDetail<T>, T> each) {
            return LoopExtensionMethods.Each<T>(collection, 0, collection.Count(), each);            
        }

        public static IEnumerable<T> Each<T>(this IEnumerable<T> collection, 
            int start, 
            Action<ElementDetail<T>, T> each) {
            return LoopExtensionMethods.Each<T>(collection, start, collection.Count(), each);
        }

        public static IEnumerable<T> Each<T>(this IEnumerable<T> collection, 
            int start, 
            int end, 
            Action<ElementDetail<T>, T> each) {

            //verify the ranges
            if (start < 0 || end > collection.Count()) {
                throw new ArgumentOutOfRangeException();
            }

            //perform the work
            foreach (T value in collection) {
                each(new ElementDetail<T>(value, start++, end, collection), value);
                if (start == end) { break; }
            }
            return collection;
        }

    }

    #endregion

    #region Detail Information Class

    /// <summary>  
    /// Contains a summary of information about the item current in the loop  
    /// </summary>  
    public class ElementDetail<T> {

        #region Constructors

        internal ElementDetail(T value, int index, int total, IEnumerable<T> collection) {
            this.Value = value;
            this.Index = index;
            this.Total = total;
            this.Collection = collection;
        }

        #endregion

        #region Loop Information

        public int Index { get; private set; }

        public int Total { get; private set; }

        public T Value { get; private set; }

        public IEnumerable<T> Collection { get; private set; }

        #endregion

        #region Value Properties

        public T Previous {
            get {
                return !this.First
                    ? this.Collection.ElementAt(this.Index - 1)
                    : default(T);
            }
        }

        public T Next {
            get {
                return !this.Last
                    ? this.Collection.ElementAt(this.Index + 1)
                    : default(T);
            }
        }

        public bool Last {
            get { return this.Index == (this.Total - 1); }
        }

        public bool First {
            get { return this.Index == 0; }
        }

        public bool Outer {
            get { return this.First || this.Last; }
        }

        public bool Inner {
            get { return !this.Outer; }
        }

        public bool Even {
            get { return this.Index % 2 == 0; }
        }

        public bool Odd {
            get { return !this.Even; }
        }

        #endregion

        #region Collection Properties

        public int StepNumber {
            get { return this.Index + 1; }
        }

        public float PercentCompleted {
            get { return (((float)this.Index / (float)this.Total) * 100); }
        }

        public float PercentRemaining {
            get { return 100 - this.PercentCompleted; }
        }

        public int StepsCompleted {
            get { return this.Index; }
        }

        public int StepsRemaining {
            get { return this.Total - this.Index; }
        }

        #endregion

    } 

    #endregion

}

Now that is a lot of code but if you review over it you’ll find that it is a set of extension methods that can be used with IEnumerable. The basic idea is that we can perform our loop within a delegate that accepts additional information about the elements in our loop.

So here is a quick example…

string[] items = {
    "Apple",
    "Orange",
    "Grape",
    "Watermellon",
    "Kiwi"
};

items.Each((item) => {
    Console.Write("{0} > ", item.Inner ? "Inner" : "Outer");
    if (!item.First) { Console.Write("Previous: {0}, ", item.Previous); }
    Console.Write("Current: {0} ({1})", item.Value, item.StepNumber);
    if (!item.Last) { Console.Write(", Next: {0}", item.Next); }
    Console.WriteLine(" -- {0}% remaining", item.PercentRemaining);
});

// Output
// Outer > Current: Apple (1), Next: Orange -- 100% remaining
// Inner > Previous: Apple, Current: Orange (2), Next: Grape -- 80% remaining
// Inner > Previous: Orange, Current: Grape (3), Next: Watermellon -- 60% remaining
// Inner > Previous: Grape, Current: Watermellon (4), Next: Kiwi -- 40% remaining
// Outer > Previous: Watermellon, Current: Kiwi (5) -- 20% remaining

Normally you would simply write all the comparisons within your loop and then use them as needed. Instead, in this code, we pass in an additional parameter that contains shortcuts to many common comparisons you might find inside of loops. By doing this we improve readability and focus on what the loop is doing.

Whats Wrong With The Old Way

Nothing! Writing your comparisons inline can be advantageous since you aren’t doing any more work than you need to do. However, in some cases, the improved readability would make a big difference in the quality of the code. Consider the two snippets of MVC code and decide with one is easier to read.

<ul>
<% foreach(SiteMapNode node in breadcrumb) { %>
    <li class="item <% =(breadcrumb.IndexOf(node) % 2 == 0 ? "item-even" : "item-odd") %>" >
    <% if (breadcrumb.First().Equals(node) || breadcrumb.Last().Equals(node)) { %>
        <strong>
    <% } %>
        <a href="<% =node.Url %>" >
            (<% =(breadcrumb.IndexOf(node) + 1) %>) : <% =node.Text %>
        </a>
    <% if (breadcrumb.First().Equals(node) || breadcrumb.Last().Equals(node)) { %>
        </strong>
    <% } %>
    </li>
<% } %>
</ul>

Or the same code using a loop helper…

<ul>
<% breadcrumb.Each((node) => { %>
    <li class="item <% =(node.Even ? "item-even" : "item-odd") %>" >
    <% if (node.Outer) { %><strong><% } %>
        <a href="<% =node.Value.Url %>" >
            (<% = node.StepNumber %>) : <% =node.Value.Text %>
        </a>
    <% if (node.Outer) { %></strong><% } %>
    </li>
<% }); %>
</ul>

This example shows using only the ElementDetail class but of course you could use the other extension method that also supplies the value by itself.

Write Code For Humans Not For Computers

Everyone has heard the advice before – more or less, readability is probably the most important part of your code. The computer can read both of those examples easily whereas a human might need to think for a moment before they are positive what the code does.

In any case, this simple but effective approach can transform previously unreadable code into works of programming art… or something like that…

Written by hugoware

September 2, 2009 at 2:12 am

WebForms And MVC In Harmony — Almost…

with 6 comments

Check out a new post about using WebControls inline with MVC that actually works with postbacks!

Pop Quiz – What happens with the following snippet of ASP.NET code?

<% int number = 5; %>
<asp:PlaceHolder runat="server" >
<% =number %>    
</asp:PlaceHolder>

Prints the number 5? Nope. Maybe it equals zero? Sorta. How about this…

Compiler Error Message: CS0103: The name ‘number’ does not exist in the current context

Yikes…

I’ve complained before about the disconnect between WebControls and actual inline code. WebControls are still a very convenient way to write templates but because they exist in a different context than inline code they are effectively off limits. As cool as MVC is you’re pretty much stuck throwing all your existing WebControls out the window. Or are you?

Using Extension Methods Instead of Controls

Extension Methods came in really at the best time possible. I can’t see MVC working without them.

If you’ve never used one before, an Extension Method lets you create a static method else where in your project, do a couple fancy assignments and then it attaches that method onto the class you’re targeting. LINQ heavily relies on Extension Methods to provide such a seamless programming experience.

One way that ASP.NET MVC uses Extension Methods is to make working with certain control types easier. For example there is a method to create the input tag, one to render a form tag, etc…

Below is an example of how you could create an Extension Method that is attached to the HtmlHelper.

public static class MyExtensionMethods {

    //example method - don't write things this ugly
    public static string BulletList(this HtmlHelper helper, params string[] items) {
        return string.Concat(
            "<ul><li>",
            string.Join("</li><li>", items),
            "</li></ul>"
            );
    }
}

In our example we create a static class to house our Extension Methods. We also create static methods with a strange argument at the start. This argument is actually the class were attaching the method to. Now we can use our code like so…

<% =this.Html.BulletList("Apple", "Orange", "Pear") %>

Cool. If you’re not familiar on the things you can do with Extension Methods then I recommend you read about them some more before you start trying to add them to your project. You could also use delegates to simulate templating within an Extension Method.

public static class MyExtensionMethods {

    //example method - renders the content of each action
    public static void TwoColumns(this HtmlHelper helper, Action left, Action right) {
        HttpContext.Current.Response.Write("<div class='left'>");
        left();
        HttpContext.Current.Response.Write("</div>");
        
        HttpContext.Current.Response.Write("<div class='right'>");
        right();
        HttpContext.Current.Response.Write("</div>");
    }
}

Then you can use your “template” like so…

<% this.Html.TwoColumns(() => { /* Left Column */ %>
    I'm on the left!
<% }, () => { /* Right Column */ %>
    I'm on the right!
<% }); /* End Two Column */ %>

Code like this can get ugly in a hurry – so be conservative in your use.

Using IDisposable To Close Tags

Another way you can create a “WebControl” with ASP.NET MVC is to create a class that implements IDisposable. By placing markup in the constructor and the Dispose method you can essentially write your RenderBeginTag() and RenderEndTag() methods you normally find on CompositeControls!

public class StyledHeader : IDisposable {

    public StyledHeader(string color) {
        HttpContext.Current.Response.Write("<h1 style='color:" + color + "' >");
    }

    public void Dispose() {
        HttpContext.Current.Response.Write("</h1>");
    }
}

Naturally, StyledHeader should have been added to the core of the ASP.NET MVC library, but somehow it got missed :). In any case, our class can be used with the using keyword to render our fancy new header.

<% using (new StyledHeader("#f00")) { %>
    Howdy - This is my header control!
<% } /* End StyledHeader */ %>

The Super Secret Final Method

As you noticed at the beginning of my post I mentioned about throwing away WebControls since they aren’t any use to us anymore. Well, that isn’t true — We can still use WebControl with our inline code for the page!

If you’ve read any of my previous blog posts, you can see that I’m a big fan of overriding the Render() method for WebControls. In similar fashion, we’re going to use the RenderControl() method to render our WebControls right when we need them.

using System.Reflection;
using System.IO;
using System.Web.UI;
using System.Web;
using System.Web.Mvc;

public static class MyExtensionMethods {

    //example method - renders a webcontrol to the page
    public static void RenderControl(this HtmlHelper helper, Control control) {

        //perform databinding if needed
        //MethodInfo bind = control.GetType().GetMethod("DataBind");
        //if (bind is System.Reflection.MethodInfo) {
        //    bind.Invoke(control, null);
        //}

        //Call a courtesy databind
        //Thanks for pointing it out Richard
        control.DataBind();
        
        //render the HTML for this control
        StringWriter writer = new StringWriter();
        HtmlTextWriter html = new HtmlTextWriter(writer);       
        control.RenderControl(html);

        //write the output 
        HttpContext.Current.Response.Write(writer.ToString());
        
        //and cleanup the writers
        html.Dispose();
        writer.Dispose();         
    }

}

You may notice the courtesy DataBind() call we’re doing there — Just in case something has a DataSource I was calling the method as well. Depending on how you use this you may want to change this some. But enough of that, how is it used?

<% int&#91;&#93; numbers = { 1, 2, 3, 4, 5 }; %>
<% this.Html.RenderControl(new DataGrid() { DataSource = numbers }); %>

You can also define your class before you pass it into the RenderControl method in case you need to do a little more to it than just assign some values to the properties.

Finally, WebForms and MVC In Harmony… Or Maybe Not…

Now I won’t pretend that you can plug all of your WebControls into this and expect it to work like WebForms used to. A lot of things are missing that a lot of WebControls rely on (like the ViewState). But, if your mainly interested in the rendered output of a WebControl then you’re in luck.

Written by hugoware

June 18, 2009 at 2:11 am

jLinq – Extending A Method

leave a comment »

It wasn’t until late into the jLinq project that I had the idea that you should be able to extend your own methods onto the main library. jLinq ended up having quite a rewrite in order to make it fit that model.

jLinq is actually entirely composed to extension methods which I suppose is a form of dog-fooding your own product. If I couldn’t do it with an extension method, then my framework didn’t expose enough to a future developer.

The jLinq Documentation section is still under-construction at this point, so this post serves as a brief introduction to extending jLinq.

jLinq allows you to extend jLinq in three separate ways.

  • Create an entirely new function in the jLinq library
  • Create a new function in a separate namespace in the jLinq library
  • Create your own library (with a copy of the existing jLinq library)

Each of these methods allow you to add one of four types of functions. This may change as time goes on to allow more methods, but for now these are what is available.

Source Commands
A source command is the first command you call when performing a jLinq query. The command .from() is a good example of a source command. Source commands return a jLinq object and any extension methods that have been provided. A source command should also set the data that is being queried

Query Commands
A query command is what sets the comparisons that are used when making a selection. Query commands are not run immediately so you are able to use operators like or() and not() to set how the query is evaluated. The criteria is not evaluated until you call a selection command which is explained more in a moment.

Action Commands
An action command affects a query or data, but doesn’t actually change what is selected. A good example is the .orderBy() command. This command resorts the information for the query, but doesn’t change what will ultimately be selected.

Selection Commands
A selection command can return anything, including the query being created. Normally, a selection command returns the results of the query as an array. Sometimes a selection command will return something different, like with commands like .count() or .isEmpty(), which return numbers and booleans.

More About Extensions

Namespaces
jLinq doesn’t allow you to overwrite a method in the core. Instead, if you want to create a command that is the same name as an existing command, you must provide a namespace to put it into. This way, naming conflicts are minimized. You access a command the same way you normally would, except you include the namespace first jLinq.from(...).custom.startsWith(...).

Custom Libraries
Another thing you can do is create a separate instance of the jLinq library under a different name (technically, you can override jLinq at that point, but that wouldn’t be very nice). If you’re working with a custom library then you can override anything (granted you don’t lock the library too, which will be explained in another post)

More Control

You can see that jLinq gives you complete control over how you use the library. Hopefully people begin to develop add-ins for jLinq that can be shared at the jLinq Message Boards. If you have questions or comments, please share them here or at the message boards. I’d love to get some feedback!

Written by hugoware

May 3, 2009 at 5:10 am