Generic Singly Linked List Implementation in C#

December 20th, 2009 Tim 1 comment

The linked list is a basic data structure that can be implemented in virtually any language. The concept is simple. A linked list consists of a collection of nodes that each point to a different node. In a singly linked list, each node points to only one other node, and that node is the next node that is in the list. Generally, a singly linked list stores a reference to the first node in the linked list, and the last object in the linked list.

In this tutorial, we are going to implement a singly linked list in C#. I hope to build upon the foundation of the linked list, and implement more data structures along the way, for example, stacks and queues. That being said, this is not going to be just a small project with two classes, but we will be defining interfaces and hopefully creating some base classes. Now that we know what to expect in the coming posts, let us begin.

By the end of this tutorial, we will aim to have a bunch of classes which look like this.

linked list class diagram

I have also laid out the structure of the files like so (just for reference).
linked list class organization

So lets begin with the interface ILinkedList<T>. This will be a generic interface which will provide the methods and properties that all linked lists that we implement should have. In the interest of space and the length of this blog post, I have left out the XML comments, but will comment on the methods as we implement them.

using System.Collections.Generic;

namespace DataStructures.LinkedList {
    public interface ILinkedList<T> : IEnumerable<T> {
        void PushFront(T item);
        void PushBack(T item);
		void InsertBefore(ILinkedListNode<T> node, ILinkedListNode<T> newNode);
        void InsertBefore(ILinkedListNode<T> node, T newObject);
        void InsertBefore(T value, ILinkedListNode<T> newNode);
        void InsertBefore(T value, T newObject);
        void InsertAfter(ILinkedListNode<T> node, ILinkedListNode<T> newNode);
        void InsertAfter(ILinkedListNode<T> node, T newObject);
        void InsertAfter(T value, ILinkedListNode<T> newNode);
        void InsertAfter(T value, T newObject);
        T PopFront();
        T PopBack();
        void Clear();
        bool IsEmpty { get; }
        int Count { get; }
        ILinkedListNode<T> Front { get; }
        ILinkedListNode<T> Back { get; }
        void Sort(IComparer<T> comparer);
    }
}

The other interfaces that we are going to be using with this tutorial is ILinkedListNode. ILinkedListNode implements INode.

namespace DataStructures {
    public interface INode<T> {
        T Value { get; set; }
    }
}
namespace DataStructures.LinkedList {
    public interface ILinkedListNode<T> : INode<T> {
    }
}

Of course, now that we have defined our interfaces, we must implement them. As I mentioned earlier, I am planning to implement different data structures, hence we will be implementing a base class for the our list. I have called my base class LinkedListBase, and the implementation is defined below.

using System.Collections.Generic;
using System.Collections;

namespace DataStructures.LinkedList.Impl {
    public abstract class LinkedListBase<T> : ILinkedList<T> {

        #region ILinkedList<T> Members

        public abstract void PushFront(T item);
        public abstract void PushBack(T item);
        public abstract void InsertBefore(ILinkedListNode<T> node, ILinkedListNode<T> newNode);
        public abstract void InsertBefore(ILinkedListNode<T> node, T newObject);
        public abstract void InsertBefore(T value, ILinkedListNode<T> newNode);
        public abstract void InsertBefore(T value, T newObject);
        public abstract void InsertAfter(ILinkedListNode<T> node, ILinkedListNode<T> newNode);
        public abstract void InsertAfter(ILinkedListNode<T> node, T newObject);
        public abstract void InsertAfter(T value, ILinkedListNode<T> newNode);
        public abstract void InsertAfter(T value, T newObject);
        public abstract T PopFront();
        public abstract T PopBack();
        public abstract void Clear();
        public bool IsEmpty {
            get { return Count == 0; }
        }
        public int Count {
            get; protected set;
        }
        public virtual ILinkedListNode<T> Front {
            get; protected set;
        }
        public virtual ILinkedListNode<T> Back {
            get; protected set;
        }
        public virtual void Sort(IComparer<T> comparer) {
            throw new System.NotImplementedException();
        }

        #endregion

        #region IEnumerable<T> Members

        public abstract IEnumerator<T> GetEnumerator();

        #endregion

        #region IEnumerable Members

        IEnumerator IEnumerable.GetEnumerator() {
            return (((IEnumerable<T>)this) as IEnumerable).GetEnumerator();
        }

        #endregion
    }
}

It is worth mentioning that the Front,Back and Count properties have the protected keyword on the setter. The reason for this is we do not want outside classes to be able to modify these values, as they are used internally within the list. The other interesting point here is that the IEnumerator GetEnumerator() method is marked as abstract while the IEnumerator GetEnumerator method has an implementation. This is because IEnumerable actually implements IEnumerable. The reason that IEnumerator GetEnumerator() is marked as abstract is that with different linked lists, we must take into account how we iterate the list. For example, caution must be taken in a cyclic linked list, as to avoid an infinite loop.

Our other base class will be the LinkedListNode.

namespace DataStructures.LinkedList.Nodes {
    public abstract class LinkedListNodeBase<T> : ILinkedListNode<T> {

        #region INode<T> Members

        public T Value {
            get; set;
        }

        #endregion
    }
}

This is straight forward. All linked list nodes need to store a value of some sort. Now we are ready to implement our actual singly linked list, and the corresponding singly linked list node.

namespace DataStructures.LinkedList.Nodes {
    public class SinglyLinkedListNode<T> : LinkedListNodeBase<T> {

        public SinglyLinkedListNode() {
        }

        public SinglyLinkedListNode(T value) {
            Value = value;
        }

        public SinglyLinkedListNode<T> Next {
            get; set;
        }

        public override bool Equals(object obj) {
            SinglyLinkedListNode<T> node = obj as SinglyLinkedListNode<T>;
            if(null == node) {
                return false;
            }
            return Value.Equals(node.Value);
        }
    }
}

In the SinglyLinkedListNode class, I have overriden Equals to compare the objects that are stored in the Value property of a node. The method then proceeds to call the Equals method on that object, and determines whether or not they are the same.

And now that we have the foundation for our linked list, we are going to implement the actual list that will be the heart of what we are doing.

using System;
using System.Collections.Generic;
using DataStructures.LinkedList.Nodes;
using DataStructures.Exception;

namespace DataStructures.LinkedList.Impl {
    public class SinglyLinkedList<T> : LinkedListBase<T> {

    }
}

Now lets start implementing the members of the class. The Front and Back properties hide their base implementations with the new keyword, but call back to the base to set the value. This allows us to cast the ILinkedListNode object into SinglyLinkedListNode, which makes it easy to work with this class.

        public new SinglyLinkedListNode<T> Front {
            get { return base.Front as SinglyLinkedListNode<T>; }
            protected set { base.Front = value; }
        }

        public new SinglyLinkedListNode<T> Back {
            get { return base.Back as SinglyLinkedListNode<T>; }
            protected set { base.Back = value; }
        }

Next, we implement the PushFront() methods. The PushFront() method allows us to add a node to the beginning of the linked list. The implementation here is simply. We must consider a few conditions. We must check whether or not the list is empty, and if so, then both the Front of the list, and the Back of the list will point to the same node. Otherwise, we just have to update the Front property and point that node’s Next property at the former Front of the list.

        public override void PushFront(T item) {
            SinglyLinkedListNode<T> node = new SinglyLinkedListNode<T>(item);
            PushFront(node);
        }

        public virtual void PushFront(SinglyLinkedListNode<T> item) {
            item.Next = Front;
            Front = item;

            if (IsEmpty) {
                Back = Front;
            }

            Count++;
        }

Next comes the implementation of adding a node to the back of the list. Here, we must check if the list is empty or not. If it is, then there will only be one node in the list after it has been added, and that will be both the Front and the Back of the list. Otherwise, if we have at least one node in the list, then the node’s last node’s Next becomes the new node, and we then just update the Back to point at the new node.

        public override void PushBack(T item) {
            SinglyLinkedListNode<T> node = new SinglyLinkedListNode<T>(item);
            PushBack(node);
        }

        public virtual void PushBack(SinglyLinkedListNode<T> item) {

            if (IsEmpty) {
                Back = item;
                Front = Back;
            } else {
                Back.Next = item;
                Back = item;
            }

            Count++;
        }

Now come the more tricky inserting methods. Inserting before a specified node, and inserting after a specified node. In the first case, there are a few things to consider. The first one is whether or not the list is empty. In our implementation, if the list is empty, then we will not be able to find any node to insert an object before, therefore, we throw an exception. Otherwise, we need to traverse the list, while keeping track of the current node that we are on, and the one before it. If we find that the current node that we are on is the node to insert before, then we take the pointer to the previous node, and do our insertion there. The insertion is similar to the way that we inserted to the front of the list. We just take the previous node’s Next pointer, point that at our new node, and point our new node’s Next property at the current node.

        public override void InsertBefore(ILinkedListNode<T> node, ILinkedListNode<T> newNode) {
            SinglyLinkedListNode<T> compareNode, current, previous = null, theNewNode;
            compareNode = node as SinglyLinkedListNode<T>;
            theNewNode = newNode as SinglyLinkedListNode<T>;

            if (IsEmpty) {
                throw new InvalidOperationException();
            }

            current = Front;
            while (current != null) {
                if (current.Equals(compareNode)) {
                    theNewNode.Next = current;
                    if (previous == null) {
                        Front = theNewNode;
                    } else {
                        previous.Next = theNewNode;
                    }
                    Count++;
                    return;
                }
                previous = current;
                current = current.Next;
            }
            throw new NodeNotFoundException<T>(node);
        }

        public override void InsertBefore(ILinkedListNode<T> node, T newObject) {
            InsertBefore(node, new SinglyLinkedListNode<T>(newObject));
        }

        public override void InsertBefore(T value, ILinkedListNode<T> newNode) {
            SinglyLinkedListNode<T> node = new SinglyLinkedListNode<T>(value);
            SinglyLinkedListNode<T> newOne = newNode as SinglyLinkedListNode<T>;
            InsertBefore(node, newOne);
        }

        public override void InsertBefore(T value, T newObject) {
            SinglyLinkedListNode<T> node = new SinglyLinkedListNode<T>(value);
            SinglyLinkedListNode<T> newObjNode = new SinglyLinkedListNode<T>(newObject);
            InsertBefore(node, newObjNode);
        }

A similar implementation exists for inserting after an object, except now you just need to keep track of the node that is one ahead, and the current node.

        public override void InsertAfter(ILinkedListNode<T> node, ILinkedListNode<T> newNode) {
            SinglyLinkedListNode<T> compareNode, current, next, theNewNode;
            compareNode = node as SinglyLinkedListNode<T>;
            theNewNode = newNode as SinglyLinkedListNode<T>;

            if (IsEmpty) {
                throw new InvalidOperationException();
            }

            current = Front;
            next = current.Next;

            while (current != null) {
                if (current.Equals(compareNode)) {
                    current.Next = theNewNode;
                    theNewNode.Next = next;

                    if (next == null) {
                        Back = theNewNode;
                    }
                    Count++;
                    return;
                }
                current = current.Next;
                next = current == null ? null : current.Next;
            }
            throw new NodeNotFoundException<T>(node);
        }

        public override void InsertAfter(ILinkedListNode<T> node, T newObject) {
            InsertAfter(node, new SinglyLinkedListNode<T>(newObject));
        }

        public override void InsertAfter(T value, ILinkedListNode<T> newNode) {
            SinglyLinkedListNode<T> node = new SinglyLinkedListNode<T>(value);
            SinglyLinkedListNode<T> newOne = newNode as SinglyLinkedListNode<T>;
            InsertAfter(node, newOne);
        }

        public override void InsertAfter(T value, T newObject) {
            SinglyLinkedListNode<T> node = new SinglyLinkedListNode<T>(value);
            SinglyLinkedListNode<T> newObjNode = new SinglyLinkedListNode<T>(newObject);
            InsertAfter(node, newObjNode);
        }

Of course, if you are able to add a node to a list, then we must be able to remove a node. Below are the implementations to removing the first node from the list, and the last node from the list. There are two differences however in these operations. When inserting into the beginning of the list, the operation is O(1), whereas inserting to the end of the list is an O(n) operation, since we must traverse the list before we are able to insert to the end. Note that in a doubly linked list, this is not the case, and that insertion to the end of the list is also an O(1) operation, since it references the node that is before the last one.

        public override T PopFront() {

            if (IsEmpty) {
                throw new InvalidOperationException("The specified list is empty.");
            }

            SinglyLinkedListNode<T> temp = Front;
            Front = Front.Next;

            Count--;

            if (Count == 0) {
                Back = Front;
            }

            return temp.Value;
        }

        public override T PopBack() {
            SinglyLinkedListNode<T> temp;

            if (IsEmpty) {
                throw new InvalidOperationException("The specified list is empty.");
            }
            if (Count == 1) {
                temp = Back;
                Front = null;
                Back = null;
            } else {
                SinglyLinkedListNode<T> current = Front;
                SinglyLinkedListNode<T> previous = null;
                while (current.Next != null) {
                    // Traverse to the last nodes in the list.
                    previous = current;
                    current = current.Next;
                }
                temp = current;
                Back = previous;
                Back.Next = null;

            }
            Count--;
            return temp.Value;
        }

The third method that we are going to implement to remove nodes from our linked list is the Clear() method. It is straight forward, since in C#, garbage collection is handled automatically for us. All we need to do is no longer reference the nodes.

        public override void Clear() {
            Front = null;
            Back = null;
            Count = 0;
        }

And finally, we must implement IEnumerable. IEnumerable allows for collections to be used in the foreach construct. The reason that I had marked this method as abstract in base class is because while the SinglyLinkedList and DoublyLinkedList implementations would have the same method, the cyclic linked list would require a different way to break out of the loop, otherwise, it would continue forever, assuming the list is not empty.

        #region IEnumerable<T> Members

        public override IEnumerator<T> GetEnumerator() {

            SinglyLinkedListNode<T> iter = Front;
            while(null != iter) {
                yield return (T)iter.Value;
                iter = iter.Next;
            }
        }

        #endregion

And there you have it. We have implemented our linked list classes, including insertion and removing of nodes, as well as laid down a foundation on which to build upon in further data structures.

I hope that this has helped, and if you have any questions or comments, or improvements to my code, feel free to leave a comment.

My Two Cents on Twitter

December 10th, 2009 Tim No comments

I recently read an article on iLounge about Twitter, entitled Twitter’s Pros and Cons: Bob, On Seriously Hating All That Twitter Stands For . I’m not going to deny what Bob has said in his article for I do agree with a large portion of it. Largely, I do believe that “the world does not need an aggregator of every few minutes of a peroson’s life”, and that there are a vast amount of useless “tweets” that exist, but this should not be a discredit to the Twitter service.

Do we necessarily need to know what everyone is doing at all times? No. Do we generally care about what people are doing? Somewhat. Do we crave information and gossip, and strive to know as much as we can? Absolutely. But is this a downfall of Twitter? Why should it be? Twitter can merely be considered a tool; a tool which is only as useful as you, the user, wants to make it. It is worth mentioning, also, that Twitter is not only used for professionals, companies, web developers, web designers, and artists, but anyone can use it. It is a free service. So why is there such hate being spawned from it? In reading Bob’s article, and in particular the area under which he addresses Twitter based milestones, I asked myself, why does it matter?

If a particular individual feels that they should make public to the world what they are doing at any given point in time, then all the power to them. It is, after all, their life – not yours. The fact that Twitter is providing an outlet for it just helps those people accomplish things that they want to in life. If it makes them happy, then all the power to them. Who cares if people are creating useless tidbits of information about their personal lives. You, the user, can choose whether or not you want to read about it.

The fact that there is a whole vocabulary that is based on Twitter is one thing, but marking a person as being a ‘twit’ for writing it is another. Take for example someone who worked as a technical writer. Would you call that person a twit if they were hired to write documentation about some piece of software? I highly doubt that you would. Think of it in the same way. Someone is being hired to write about Twitter. Or rather, think of them as someone who works in sales. It could be a means of getting the thing big. At the end of the day, someone did it, whether they enjoyed to do it, or were being paid for it. The fact that someone didnt’t like it, doesn’t mean that what they did was useless. That would be the equivalent of me telling an architect that his building is useless because it isn’t appealing to my eye.

At the end of the day however, there are many uses of Twitter. As an example, I personally use Twitter to follow many companies that I have interest in, or follow individuals who have a history of making posts of interest to me. Do I go and follow every person who follows me, or follow everyone who I can find? Absolutely not – the reason being that it serves little interest to me. I do, however, use it to cultivate information, and stay in the loop about things – mainly technologically related. Sometimes, Twitter is just more useful than say an RSS feed for a blog.

Take for example small mobile gaming application companies. Twitter is often useful for them, since they would be able to post information quickly, and spread it to a mass amount of people, who already use an existing service. One could post about updates, expected patches, changes, etc. without the need for a formal blog post.

Blogs can be expensive to create, time consuming to update, and often times just a pain in the ass, when all you want to say are a few lines. Why subject people to have to use an RSS feed, when the convenience can be given to them on their doorstep from something that they already use? Of course, blogs are their own matter, and should most likely be separated into a different discussion.

But at the end of the day, Twitter is just another tool in the world of social media. It is up to the user to decide on how they want to use it, what type of information they wish to follow, and what type of information they wish to convey. Millions of people are online everyday, and one person just can’t satisfy the masses. All they can do is tweet about what is of interest to them, and hope that their information is inspiring, important, or maybe even remotely of interest to someone else.

Categories: Social Tags: , ,

Using IPostBackEventHandler to perform postbacks from Javascript

December 5th, 2009 Tim 1 comment

A few times, I have found myself in a situation where I need to do post back to the server and don’t want to explicitly call the __doPostBack function. .NET provides a way to accomplish this easily, by implementing an interface, IPostBackEventHandler.

IPostBackEventHandler defines one method,

void RaisePostBackEvent(string eventArgument);

When implemented by a page’s code behind class, it is then possible to post back to that page through javascript.

function DoPostback() {
    <%= Page.Clientscript.GetPostBackEventReference(this, "arguments") %>
}

After calling this function, the method that was implemented for the IPostbackEventHandler will be invoked, and “arguments” will be passed in as the eventArgument parameter. Of course, you can pass in different arguments to call different functions.

public partial class Page : IPostBackEventHandler {

    #region IPostBackEventHandler Members

    public void RaisePostBackEvent(string eventArgument) {
        if(eventArgument.Equals("DoThingOne")) {
            DoThisFunction();
        } else if(eventArgument.Equals("DoThingTwo")) {
            DoThisOtherFunction();
        }
    }

    #endregion
}

There are limitations to this, however. The first and foremost being that you can not easily pass local values from javascript to the function, due to the fact that the GetPostBackEventReference method is executed at load time, and not at run time. The fact that it is contained in <%= %> tags says to output the result of the function call onto this part of the page.

Fear not! There are ways to get around this. If you must pass additional parameters (on top of what you already get for free with the viewstate being passed back, since we are doing a full blown postback), you can specify values in hidden fields on your page.

<asp:HiddenField runat="server" id="hdnParam" />

You can set the values of the hidden fields easily through javascript. Since it is known that the HiddenField is a server control, the ID is not what will be generated on the page. Therefore, in order to set it in javascript, the ClientID must be resolved for the hidden field, before the control can be manipulated. The code example below demonstrates how this can be accomplished in javascript.

function DoPostBackWithParameters() {
    var hdnField = document.getElementById('<%= hdnParam.ClientID %>');
    hdnField.value = "arbitrary value";
    <%= Page.Clientscript.GetPostBackEventReference(this, "arguments") %>
}

Now that a value has been set for a hidden field, you can retrieve it from your code behind, like so.

public void RaisePostbackEvent(string eventArgument) {
    string parameters = hdnField.Value;
    // I always like to clear the hidden field once I am done with it.
    hdnField.Value = string.Empty;
}

So while there are limitations in what you can do with this, it is an easy way to perform a post back, have full viewstate, as well as be able to specify parameters.

Finding duplicate entries in a SQL table

December 5th, 2009 Tim 1 comment

Sometimes, it is useful to be able to query a database and see what duplicate entries exist for a given column in a database table.

The following query will return to you the value(s) that exist more than once in a column.

select column_name
from table_name
group by column_name
having (count(column_name) > 1)
Categories: SQL Tags: , ,