CodeBase

An open source project to have all common algorithms implemented in all languages.

Github project page: https://github.com/shadinamrouti/CodeBase

MIT License

Copyright (c) 2019 Shadi Namrouti

Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:

The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

csharp

Common: LinkedList: Recursion Iteration Delegates: Sort: Stack and Queue:

csharp

Print

                        

using System;

namespace Codebase
{
    public static partial class Common
    {
        public static void Print<T>(this T[] array, string delimiter=" ") 
        {
            for (int i = 0; i < array.Length; i++)
                Console.Write(array[i] + delimiter);

            Console.WriteLine();
        }

        public static void Print<T>(this T item, string delimiter="\n")
        {
            Console.Write(item + delimiter);
        }

    }
}


Random

                        

using System;

namespace Codebase
{
    public static partial class Common
    {
        public static int RandomInt(int min = 0, int max = Int32.MaxValue)
        {
            Random rnd = new Random();
            return (dynamic)rnd.Next(0, max);
        }

        public static double RandomDouble(int decimalPlaces = 1)
        {
            Random rnd = new Random();
            return Math.Round(rnd.NextDouble(), decimalPlaces);
        }

        public static int[] RandomArrayInt(int count, int min = 0, int max = Int32.MaxValue)
        {
            int[] array = new int[count];

            for (int i = 0; i < count; i++)
                array[i] = RandomInt(min, max);

            return array;
        }

        public static double[] RandomArrayDouble(int count, int decimalPlaces = 1)
        {
            double[] array = new double[count];

            for (int i = 0; i < count; i++)
                array[i] = RandomDouble(decimalPlaces);

            return array;
        }

        public static T RandomNumber<T>(int min = 0, int max = Int32.MaxValue, int decimalPlaces = 1)
        {
            if (typeof(T) == typeof(System.Int32))
                return (dynamic)RandomInt(min, max);
            else //if (typeof(T) == typeof(System.Double))
                return (dynamic)RandomDouble(decimalPlaces);
        }

        public static T[] RandomArray<T>(int count, int min = 0, int max = Int32.MaxValue, int decimalPlaces = 1)
        {
            T[] array = new T[count];

            if (typeof(T) == typeof(System.Int32))
                for (int i = 0; i < count; i++)
                    array[i] = (dynamic)RandomInt(min, max);
            else //if (typeof(T) == typeof(System.Double))
                for (int i = 0; i < count; i++)
                    array[i] = (dynamic)RandomDouble(decimalPlaces);

            return array;
        }
    }
}


Swap

                        

using System;

namespace Codebase
{
    public static partial class Common
    {
        public static void Swap<T>(ref T a, ref T b) where T: struct
        {
            T temp = a;
            a = b;
            b = temp;
        }

    }
}


BinarySearchTree

                        

using System;
using System.Collections.Generic;

namespace Codebase.Trees
{
    public class Node
    {
        public int Key { get; set; }
        public Node Left { get; set; }
        public Node Right { get; set; }

        public Node()
        {
        }

        public Node(int key, Node left = null, Node right = null)
        {
            this.Key = key;
            this.Left = left;
            this.Right = right;
        }
    }

    public class Tree
    {
        private Node Root { get; set; }
        
        public void PreOrder()
        {
            Console.Write(nameof(PreOrder) + ": ");
            PreOrder(Root);
        }

        public void InOrder()
        {
            Console.Write(nameof(InOrder) + ": ");
            InOrder(Root);
        }

        public void PostOrder()
        {
            Console.Write(nameof(PostOrder) + ": ");
            PostOrder(Root);
        }

        public void Insert(int key)
        {
            Root = Insert(Root, key);
        }

        public Node Search(int key)
        {
            Node item = Search(Root, key);
            return item;
        }



        #region private methods
        private Node Search(Node node, int key)
        {
            if (node == null || node.Key == key)
                return node;

            if (key < node.Key)
                return Search(node.Left, key);
            else
                return Search(node.Right, key);
        }

        private void PreOrder(Node node)
        {
            if (node != null)
            {
                Console.Write(node.Key + " ");
                PreOrder(node.Left);
                PreOrder(node.Right);
             }
        }

        
        private void InOrder(Node node)
        {
            if (node != null)
            {
                InOrder(node.Left);
                Console.Write(node.Key + " ");
                InOrder(node.Right);
            }
        }

        private void PostOrder(Node node)
        {
            if (node != null)
            {
                PostOrder(node.Left);
                PostOrder(node.Right);
                Console.Write(node.Key + " ");
            }
        }
        
        private Node Insert(Node node, int data)
        {
            if (node == null)
            {
                node = new Node(data);
                return node;
            }

            if (data < node.Key)
                node.Left = Insert(node.Left, data);
            else
                node.Right = Insert(node.Right, data);

            return node;
        }
        #endregion
    }
}


LinkedList

                        

using System;
using System.Collections.Generic;

namespace Codebase.LinkedLists
{
    public class Node
    {
        public object Data { get; set; }
        public Node Next { get; set; }

        public Node()
        {
        }

        public Node(object Data, Node Next = null)
        {
            this.Data = Data;
            this.Next = Next;
        }
    }

    public class LinkedList
    {
        private Node Head { get; set; }

        public Node First
        {
            get => Head;
            set
            {
                First.Data = value.Data;
                First.Next = value.Next;
            }
        }

        public Node Last
        {
            get
            {
                Node node = Head;
                //Based partially on https://en.wikipedia.org/wiki/Linked_list
                while (node.Next != null)
                    node = node.Next; //traverse the list until p is the last node.The last node always points to NULL.

                return node;
            }
            set
            {
                Last.Data = value.Data;
                Last.Next = value.Next;
            }
        }

        public void AddFirst(Object data, bool verbose = true)
        {
            Head = new Node(data, Head);
            if (verbose) Print();
        }

        public void AddFirst(Node newHead, bool verbose = true)
        {
            newHead.Next = Head;
            Head = newHead;
            if (verbose) Print();
        }

        public void AddLast(Object data, bool Verbose = true)
        {
            Last.Next = new Node(data);
            if (Verbose) Print();
        }

        public Node RemoveFirst(bool verbose = true)
        {
            Node first = First;
            Head = First.Next;
            if (verbose) Print();
            return first;
        }

        public Node RemoveLast(bool verbose = true)
        {
            Node parent = Head;
            Node last = Last;

            while (parent.Next != last)
                parent = parent.Next;

            parent.Next = null;
            if (verbose) Print();

            return last;
        }

        public void AddAfter(Node parent, object data, bool verbose = true)
        {
            Node child = new Node()
            {
                Data = data,
                Next = parent.Next //it becomes the parent of the original child
            };

            parent.Next = child;

            if (verbose) Print();
        }

        public void AddBefore(Node child, object data, bool verbose = true)
        {
            Node parent = Head;

            while (parent.Next != child) //Finding the parent 
            {
                parent = parent.Next;
            }

            Node newParent = new Node
            {
                Data = data,
                Next = child //same as  = parent.Next
            };

            //Reattach the original parent to the new parent
            parent.Next = newParent;

            if (verbose) Print();
        }

        public Node Find(object data)
        {
            Node node = Head;

            while (node != null)
            {
                if (node.Data == data)
                    return node;

                node = node.Next;
            }
            return null;
        }

        public void Remove(Node child, bool verbose = true)
        {
            Node parent = Head;

            while (parent.Next != child)
            {
                parent = parent.Next;
            }

            parent.Next = child.Next; //jump over the node-to-be-removed
            if (verbose) Print();
        }

        public void Print()
        {
            Node node = Head;
            while (node != null) //LinkedList iterator
            {
                Console.Write(node.Data + " ");
                node = node.Next; //traverse the list until p is the last node.The last node always points to NULL.
            }
            Console.WriteLine();
        }
    }
}


Fact

                        

using System;

namespace Codebase
{
    public static partial class Recursion
    {
        //Delegate: Defaulted to recursive version
        delegate int FactDelegate(int item);
        public static int Fact(int item, bool isRecursion = true)
        {
            FactDelegate factDelegate;

            if (isRecursion)
                factDelegate = new FactDelegate(FactRecursion);
            else
                factDelegate = new FactDelegate(FactIterative);

            return factDelegate(item);
        }

        //Recursive
        public static int FactRecursion(int item) 
        {
            if (item == 0 || item == 1)
                return 1;
            else
                return item * FactRecursion(item - 1);
        }

        //Iterative
        public static int FactIterative(int item)
        {
            int Fact = 1;

            for (int i = item; i >= 1; i--)
                Fact *= i;

            return Fact;
        }
    }
}


Fib

                        

using System;

namespace Codebase
{
    public static partial class Recursion
    {
        delegate int FibDelegate(int n);

        public static int Fib(int n, bool isRecursive = true)
        {
            FibDelegate fibDelegate;

            if (isRecursive)
                fibDelegate = new FibDelegate(FibRecursive);
            else
                fibDelegate = new FibDelegate(FibIterative);

            return fibDelegate(n);
        }

        //Recursive
        public static int FibRecursive(int n)
        {
            if (n < 2)
                return n;
            else
                return FibRecursive(n - 2) + FibRecursive(n - 1);
        }

        //Iterative
        public static int FibIterative(int n)
        {
            if (n < 2)
                return n;

            int fibN_2 = 0;
            int fibN_1 = 1;
            
            int fibN = 0;
            for (int i = 2; i <= n; i++)
            {
                fibN = fibN_2 + fibN_1;

                //Shifting fibN_2 and fibN_1 for next iteration
                fibN_2 = fibN_1;
                fibN_1 = fibN;
            }

            return fibN;
        }
    }
}


Sum

                        

using System;

namespace Codebase
{
    public static partial class Recursion
    {
        delegate int SumDelegate(int start, int end, int step);

        public static int Sum(int start, int end, int step, bool isRecursive = true)
        {
            SumDelegate sumDelegate;

            if (isRecursive)
                sumDelegate = new SumDelegate(SumRecursive);
            else
                sumDelegate = new SumDelegate(SumIterative);

            return sumDelegate(start, end, step);
        }

        //Recursive
        public static int SumRecursive(int start, int end, int step) 
        {
            if (start<=end)
                return start + SumRecursive(start + step, end, step);
            else
                return 0;
        }

        //Iterative
        public static int SumIterative(int start, int end, int step)
        {
            int Sum = 0;

            for (int i = start; i <= end; i += step)
                Sum += i;

            return Sum;
        }
        
    }
}


BogoSort

                        

using System;

namespace Codebase
{
    public static partial class Sort
    {
        public static void BogoSort<T>(this T[] a, bool verbose = true) where T : struct
        {
            if (verbose)
            {
                Console.WriteLine(nameof(BogoSort));
                a.Print();
            }

            //Based on https://en.wikipedia.org/wiki/Bogosort

            while (!a.IsArraySorted())
            {
                a.ShuffleArray();
                if (verbose) a.Print();
            }
        }

        private static bool IsArraySorted<T>(this T[] a)
        {
            bool isSorted = true;

            for (int i = 0; i < a.Length - 1; i++)
                if ((dynamic)a[i] > a[i + 1])
                    isSorted = false;
            return isSorted;

            //Note the return can be used immediately inside the loop
            //But this was avoided because in JQuery there is a problem doing so 
            //i.e. if someone wants to mirror the JQuery version
        }

        //Based on https://en.wikipedia.org/wiki/Bogosort
        //Recreates a list in random order by removing elements in random positions
        private static T[] ShuffleArray<T>(this T[] a)
        {
            T[] newList = new T[a.Length];
            int[] usedIndecies = new int[a.Length];

            int index = -1;
            int randomPosition = 0;

            while (index < a.Length - 1)
            {
                randomPosition = Common.RandomInt(0, a.Length);

                if (!IsFound(usedIndecies, index, randomPosition))
                {
                    index++;
                    newList[index] = a[randomPosition];
                    usedIndecies[index] = randomPosition;
                }
            }

            Array.Copy(newList,a,a.Length);

            return newList;
        }

        private static bool IsFound(int[] exceptionsIndices, int lastIndexToSearch, int randomPosition)
        {
            bool found = false;

            for (int i = 0; i <= lastIndexToSearch; i++)
                if (randomPosition == exceptionsIndices[i])
                    found = true;

            return found;
        }
    }
}


BubbleSort

                        

using System;

namespace Codebase
{
    public static partial class Sort
    {

        public static void BubbleSort<T>(this T[] a, bool verbose = true) where T : struct
        {
            if (verbose)
            {
                Console.WriteLine(nameof(BubbleSort));
                a.Print();
            }

            //Based on https://en.wikipedia.org/wiki/Bubble_sort
            int n = a.Length;
            bool swapped = false;

            do
            {
                swapped = false;
                for (int i = 1; i <= n - 1; i++)
                {
                    /* if this pair is out of order */
                    if ((dynamic)a[i - 1] > a[i])
                    {

                        /* swap them and remember something changed */
                        Common.Swap(ref a[i - 1], ref a[i]);
                        swapped = true;

                        if (verbose) a.Print();
                    }

                }
            } while (swapped);

        }

        public static void BubbleSortV2<T>(this T[] a, bool verbose = true) where T : struct
        {
            if (verbose)
            {
                Console.WriteLine(nameof(BubbleSortV2));
                a.Print();
            }

            //Based on https://en.wikipedia.org/wiki/Bubble_sort
            int n = a.Length;
            bool swapped = false;

            do
            {
                swapped = false;
                for (int i = 1; i <= n - 1; i++)
                {
                    /* if this pair is out of order */
                    if ((dynamic)a[i - 1] > a[i])
                    {

                        /* swap them and remember something changed */
                        Common.Swap(ref a[i - 1], ref a[i]);
                        swapped = true;

                        if (verbose) a.Print();
                    }
                }
                n--;
            } while (swapped);

        }

        public static void BubbleSortV3<T>(this T[] a, bool verbose = true) where T : struct
        {
            if (verbose)
            {
                Console.WriteLine(nameof(BubbleSortV3));
                a.Print();
            }
            //Based on https://en.wikipedia.org/wiki/Bubble_sort
            int n = a.Length;
            do
            {
                int newn = 0;
                for (int i = 1; i <= n - 1; i++)
                {
                    /* if this pair is out of order */
                    if ((dynamic)a[i - 1] > a[i])
                    {
                        /* swap them and remember something changed */
                        Common.Swap(ref a[i - 1], ref a[i]);
                        newn = i;

                        if (verbose) a.Print();
                    }
                }
                n = newn;
            } while (n > 1);
        }
    }
}


CombSort

                        

using System;

namespace Codebase
{
    public static partial class Sort
    {

        public static void CombSort<T>(this T[] a, bool verbose = true) where T : struct
        {
            if (verbose)
            {
                Console.WriteLine(nameof(CombSort));
                a.Print();
            }

            //Based on https://en.wikipedia.org/wiki/Comb_sort
            double gap = a.Length; // Initialize gap size
            double shrink = 1.3; // Set the gap shrink factor
            bool sorted = false;

            while (!sorted)
            {
                // Update the gap value for a next comb
                gap = Math.Floor(gap / shrink);
                if (gap <= 1)
                {
                    gap = 1;
                    sorted = true; // If there are no swaps this pass, we are done
                }

                // A single "comb" over the input list
                int i = 0;

                while (i + gap < a.Length)
                {

                    while (i + gap < a.Length) // See Shell sort for a similar idea
                    {
                        if ((dynamic)a[i] > a[i + (int)gap])
                        {
                            Common.Swap(ref a[i], ref a[i + (int)gap]);
                            sorted = false;
                            // If this assignment never happens within the loop,
                            // then there have been no swaps and the list is sorted.

                            if (verbose) a.Print();
                        }

                        i++;
                    }
                }
            }
        }
    }
}


InsertionSort

                        

using System;

namespace Codebase
{
    public static partial class Sort
    {
        public static void InsertionSort<T>(this T[] a, bool verbose = true) where T : struct
        {
            if (verbose)
            {
                Console.WriteLine(nameof(InsertionSort));
                a.Print();
            }

            //Based on https://en.wikipedia.org/wiki/Insertion_sort
            for (int i = 1; i < a.Length; i++)
                for (int j = i; j > 0 && (dynamic)a[j - 1] > a[j]; j--)
                {
                    Common.Swap(ref a[j], ref a[j - 1]);
                    if (verbose) a.Print();
                }
        }

        public static void InsertionSortV2<T>(this T[] a, bool verbose = true) where T : struct
        {
            if (verbose)
            {
                Console.WriteLine(nameof(InsertionSortV2));
                a.Print();
            }

            //Based on https://en.wikipedia.org/wiki/Insertion_sort
            for (int i = 1; i < a.Length; i++)
            {
                T temp = a[i];
                int j = i - 1;
                for (; j >= 0 && (dynamic)a[j] > temp; j--)
                {
                    a[j + 1] = a[j];
                }

                a[j + 1] = temp;
                if (verbose) a.Print();
            }
        }

        public static void InsertionSortV3<T>(this T[] a, bool verbose = true) where T : struct
        {
            if (verbose)
            {
                Console.WriteLine(nameof(InsertionSortV3));
                a.Print();
            }

            InsertionSortV3Recursive(a, a.Length - 1, verbose);
        }

        private static void InsertionSortV3Recursive<T>(T[] a, int n, bool verbose) where T : struct
        {
            //Based on https://en.wikipedia.org/wiki/Insertion_sort
            if (n > 0)
                InsertionSortV3Recursive(a, n - 1, verbose);

            T temp = a[n];
            int j = n - 1;
            for (; j >= 0 && (dynamic)a[j] > temp; j--)
            {
                a[j + 1] = a[j];
            }

            a[j + 1] = temp;
            if (verbose) a.Print();
        }

    }
}


QuickSort

                        

using System;

namespace Codebase
{
    public static partial class Sort
    {

        //Based on https://en.wikipedia.org/wiki/Quicksort
        //Used lomuto partition scheme (see Wikipedia)
        public static void QuickSort<T>(this T[] a, bool verbose = true) where T : struct
        {
            if (verbose)
            {
                Console.WriteLine(nameof(QuickSort));
                a.Print();
            }

            QuickSort(a, 0, a.Length - 1, verbose);
        }

        public static void QuickSort<T>(this T[] a, int lo, int hi, bool verbose = true) where T : struct
        {

            if (lo < hi)
            {
                int pivot = Partition(a, lo, hi, verbose);

                QuickSort(a, lo, pivot - 1, verbose);
                QuickSort(a, pivot + 1, hi, verbose);

            }

        }

        //Based on https://en.wikipedia.org/wiki/Quicksort
        private static int Partition<T>(T[] a, int lo, int hi, bool verbose = true) where T : struct
        {
            T pivot = a[hi];
            int i = lo;

            for (int j = lo; j <= hi - 1; j++)
                if ((dynamic)a[j] < pivot)
                {
                    Common.Swap(ref a[i], ref a[j]);
                    if (verbose) a.Print();

                    i++;
                }

            Common.Swap(ref a[i], ref a[hi]);
            if (verbose) a.Print();

            return i;
        }


        //Based on https://en.wikipedia.org/wiki/Quicksort
        //Used Hoare partition scheme (see Wikipedia)
        public static void QuickSortV2<T>(this T[] a, bool verbose = true) where T : struct
        {
            if (verbose)
            {
                Console.WriteLine(nameof(QuickSortV2));
                a.Print();
            }

            QuickSortV2(a, 0, a.Length - 1, verbose);
        }

        public static void QuickSortV2<T>(this T[] a, int lo, int hi, bool verbose = true) where T : struct
        {

            if (lo < hi)
            {
                int pivot = PartitionV2(a, lo, hi, verbose);

                QuickSortV2(a, lo, pivot, verbose);
                QuickSortV2(a, pivot + 1, hi, verbose);

            }

        }

        //Based on https://en.wikipedia.org/wiki/Quicksort
        private static int PartitionV2<T>(T[] a, int lo, int hi, bool verbose = true) where T : struct
        {
            T pivot = a[(lo + hi) / 2];

            int i = lo - 1;
            int j = hi + 1;

            while (true)
            {
                do
                {
                    i++;
                } while ((dynamic)a[i] < pivot);

                do
                {
                    j--;
                } while ((dynamic)a[j] > pivot);

                if (i >= j)
                    return j;

                Common.Swap(ref a[i], ref a[j]);
                if (verbose) a.Print();
            }

        }
    }
}


SelectionSort

                        

using System;

namespace Codebase
{
    public static partial class Sort
    {
        public static void SelectionSort<T>(this T[] a, bool verbose = true) where T : struct
        {
            if (verbose)
            {
                Console.WriteLine(nameof(SelectionSort));
                a.Print();
            }

            //Based on https://en.wikipedia.org/wiki/Selection_sort
            /* a[0] to a[n-1] is the array to sort */

            int n = a.Length; // initialise to a's length

            /* advance the position through the entire array */
            /*   (could do j < n-1 because single element is also min element) */
            for (int j = 0; j < n - 1; j++)
            {
                /* find the min element in the unsorted a[j .. n-1] */

                /* assume the min is the first element */
                int iMin = j;
                /* test against elements after j to find the smallest */
                for (int i = j + 1; i < n; i++)
                {
                    /* if this element is less, then it is the new minimum */
                    if ((dynamic)a[i] < a[iMin])
                    {
                        /* found new minimum; remember its index */
                        iMin = i;
                    }
                }

                if (iMin != j)
                {
                    Common.Swap(ref a[j], ref a[iMin]);
                    if (verbose) a.Print();
                }
            }
        }


        public static void BingoSort<T>(this T[] a, bool verbose = true) where T : struct
        {
            if (verbose)
            {
                Console.WriteLine(nameof(BingoSort));
                a.Print();
            }

            //Based on https://en.wikipedia.org/wiki/Selection_sort
            //This procedure sorts in ascending order.
            int max = a.Length - 1;
            //The first iteration is written to look very similar to the subsequent ones, but  without swaps. 
            T nextValue = a[max];

            for (int i = max - 1; i >= 0; i--)
                if ((dynamic)a[i] > nextValue)
                    nextValue = a[i];

            while (max > 0 && (dynamic)a[max] == nextValue)
                max--;

            while (max > 0)
            {
                T value = nextValue;
                nextValue = a[max];

                for (int i = max - 1; i >= 0; i--)
                    if ((dynamic)a[i] == value)
                    {
                        Common.Swap(ref a[i], ref a[max]);
                        if (verbose) a.Print();

                        max--;

                    }
                    else if ((dynamic)a[i] > nextValue)
                        nextValue = a[i];


                while (max > 0 && (dynamic)a[max] == nextValue)
                    max--;
            }
        }
    }
}

Queue

                        

using System;

namespace Codebase
{
    //Based on https://en.wikipedia.org/wiki/Queue_(abstract_data_type)
    public class QueueArray<T>
    {
        private readonly T[] Items;
        private int QFront;
        private int QRear;
        private readonly int MaxSize;

        public QueueArray(int maxSize)
        {
            MaxSize = maxSize;
            Items = new T[maxSize];
            QFront = 0;
            QRear = 0;
        }

        public void Enqueue(T item)
        {
            if (IsFull())
                throw new Exception("Overflow!");
            else
                Items[QRear] = item;

            QRear++;
        }

        public T Dequeue()
        {
            T item;
            if (IsEmpty())
                throw new Exception("Underflow!");
            else
                item = Items[QFront];

            QFront++;

            return item;
        }

        public bool IsEmpty()
        {
            return QRear == QFront;
        }

        public bool IsFull()
        {
            return QRear == MaxSize;
        }

        public void Print()
        {
            Items.Print();
        }

        public int Size()
        {
            return QRear - QFront;
        }

        public T OnRear()
        {
            return Items[QRear];
        }

        public T OnFront()
        {
            return Items[QFront];
        }


    }


    public class QueueArrayCircular<T>
    {
        private readonly T[] Items;
        private int QFront;
        private int QRear;
        private readonly int MaxSize;

        public QueueArrayCircular(int maxSize)
        {
            MaxSize = maxSize;
            Items = new T[maxSize];
            QFront = 0;
            QRear = 0;
        }

        public void Enqueue(T item)
        {
            if (IsFull())
                throw new Exception("Overflow!");
            else
                Items[QRear] = item;


            if (QRear == MaxSize - 1)
                QRear = 0;
            else
                QRear++;
        }

        public T Dequeue()
        {
            T item;

            if (IsEmpty())
                throw new Exception("Underflow!");
            else
                item = Items[QFront];

            if(QFront == MaxSize - 1)
                QFront = 0;
            else
                QFront++;

            return item;
        }

        public bool IsEmpty()
        {
            return QRear == QFront;
        }

        public bool IsFull()
        {
            return (QFront == 0 && QRear == MaxSize - 1) || (QRear == QFront - 1);
        }

        public void Print()
        {
            int counter = QFront;

            while (counter == QRear)
            {
                Common.Print(Items[counter]);

                if (counter == MaxSize - 1)
                    counter = 0;
                else
                    counter++;
            }

        }

        public int Size()
        {
            return Math.Abs(QRear - QFront);        
        }

        public T OnRear()
        {
            return Items[QRear];
        }

        public T OnFront()
        {
            return Items[QFront];
        }
        
    }
}


Stack

                        

using System;

namespace Codebase
{
    //Based https://en.wikipedia.org/wiki/Stack_(abstract_data_type)
    public class StackArray<T>
    {
        private readonly T[] Items;
        private int StackTop;
        private readonly int MaxSize;

        public StackArray(int maxSize)
        {
            MaxSize = maxSize;
            Items = new T[maxSize];
            StackTop = 0;
        }

        public void Push(T item)
        {
            if (IsFull())
                throw new Exception("Overflow!");
            else
                Items[StackTop] = item;

            StackTop++;
        }

        public T Pop()
        {
            T item;

            if (IsEmpty())
                throw new Exception("Underflow!");
            else
            {
                --StackTop;
                item = Items[StackTop];
            }

            return item;

        }

        public bool IsEmpty()
        {
            return StackTop == 0;
        }

        public bool IsFull()
        {
            return StackTop == MaxSize;
        }

        public void Print()
        {
            Items.Print();
        }

        public int Size()
        {
            return StackTop + 1;
        }

        public T OnTop()
        {
            return Items[StackTop];
        }

    }
}