Field Notes
Engineering

Stack and Queue in C#

Linked-list implementations of a stack and a queue.

2 min read

Stack ​

c#
namespace DataStructure
{
    internal class Program
    {
        // type parameter T in angle brackets
        public class GenericList<T>
        {
            // The nested class is also generic on T.
            private class Node
            {
                // T used in non-generic constructor.
                public Node(T t)
                {
                    next = null;
                    data = t;
                }

                private Node? next;
                public Node? Next
                {
                    get { return next; }
                    set { next = value; }
                }

                // T as private member data type.
                private T data;

                // T as return type of property.
                public T Data
                {
                    get { return data; }
                    set { data = value; }
                }
            }

            private Node? head;

            // constructor
            public GenericList()
            {
                head = null;
            }

            // T as method parameter type:
            public void AddHead(T t)
            {
                Node n = new Node(t);
                n.Next = head;
                head = n;
            }

            public IEnumerator<T> GetEnumerator()
            {
                Node? current = head;

                while (current != null)
                {
                    yield return current.Data;
                    current = current.Next;
                }
            }
        }
        static void Main(string[] args)
        {
            // int is the type argument
            GenericList<int> list = new GenericList<int>();

            for (int x = 0; x < 10; x++)
            {
                list.AddHead(x);
            }

            foreach (int i in list)
            {
                System.Console.Write(i + " ");
            }
            System.Console.WriteLine("\nDone");
        }
    }
}

Queue ​

c#
namespace DataStructure
{
    internal class Program
    {
        // type parameter T in angle brackets
        public class GenericList<T>
        {
            private class Node
            {
                public Node(T t)
                {
                    Next = null;
                    Data = t;
                }

                public Node? Next { get; set; }
                public T Data { get; set; }
            }

            private Node? head;
            private Node? tail;

            // Constructor
            public GenericList()
            {
                head = null;
                tail = null;
            }

            // Add a node at the tail (for queue behavior)
            public void AddTail(T t)
            {
                Node newNode = new Node(t);
                if (tail != null)
                {
                    tail.Next = newNode;
                }
                tail = newNode;
                if (head == null)
                {
                    head = newNode;
                }
            }

            // Enumerator to iterate through the list
            public IEnumerator<T> GetEnumerator()
            {
                Node? current = head;
                while (current != null)
                {
                    yield return current.Data;
                    current = current.Next;
                }
            }
        }
        static void Main(string[] args)
        {
            // int is the type argument
            GenericList<int> list = new GenericList<int>();

            for (int x = 0; x < 10; x++)
            {
                list.AddTail(x);
            }

            foreach (int i in list)
            {
                System.Console.Write(i + " ");
            }
            System.Console.WriteLine("\nDone");
        }
    }
}