public static void Process(Node node, int maxValue)
 {
     if (node.Value < maxValue)
     {
         Console.WriteLine(node.Value);
     }
 }
        public static void DepthFirstRecursiveTraverse(Node root, int maxValue)
        {
            if (root == null) return;

            Process(root, maxValue);
            if (root.Left != null) DepthFirstRecursiveTraverse(root.Left, maxValue);
            if (root.Right != null) DepthFirstRecursiveTraverse(root.Right, maxValue);
        }
        public static void DepthFirstNonRecursiveTraverse(Node root, int maxValue)
        {
            var nodes = new Stack<Node>();
            nodes.Push(root);

            while (nodes.Count > 0)
            {
                var cur = nodes.Pop();
                Process(cur, maxValue);
                if (cur.Left != null) nodes.Push(cur.Left);
                if (cur.Right != null) nodes.Push(cur.Right);
            }
        }
 public static void BreadthFirstNonRecursive(Node root, int maxValue)
 {
     if (root == null) return;
     var queue = new Queue<Node>();
     queue.Enqueue(root);
     while (queue.Count > 0)
     {
         var cur = queue.Dequeue();
         Process(root, maxValue);
         if (cur.Left != null) queue.Enqueue(cur.Left);
         if (cur.Right != null) queue.Enqueue(cur.Right);
     }
 }
        public static Node GetRandomList(int count)
        {
            if (count < 0) throw new ArgumentOutOfRangeException("count");
            if (count == 0) return null;

            var current = new Node { Child = null, Value = 0 };
            var root = current;

            for (var i = 1; i < count; i++)
            {
                current.Child = new Node { Child = null, Value = i };
                current = current.Child;
            }

            return root;
        }
        // Neither cpu nor resource hungry
        public static Node Reverse(Node root)
        {
            if (root == null || root.Child == null) return root;

            var cur = root;
            Node prev = null;

            // n 1-2 2-3 3-4 4-n
            while (cur != null)
            {
                var next = cur.Child;
                cur.Child = prev;
                prev = cur;
                cur = next;
            }

            return prev;
        }
        //        public static Node CpuHungryReverse(Node root)
        //        {
        //              // get_last() traverse throught he list and return last and one before
        //              // last items (or null if there are only one item in the list)
        //
        //              last, prev = root.get_last()
        //              new_root = last
        //            
        //              while prev != null:
        //                  prev.Child = null
        //                  last.Child = prev
        //                  last, prev = list.get_two_last_items()
        //            
        //              return new_root
        //        }
        //        public static Node MemoryHungryReverse(Node root)
        //        {
        //            var items = new Stack<Node>();
        //            var cur = root;
        //
        //            while (cur != null)
        //            {
        //                items.push(cur);
        //                cur = cur.Child;
        //            }
        //
        //            var newRoot = stack.Peek();
        //            cur = newRoot;
        //            
        //            while (stack.Count > 0)
        //            {
        //                cur.Child = stack.Pop();
        //                cur = cur.Child;
        //            }
        //
        //            return newRoot;
        //        }
        private static void PrintNodes(Node root)
        {
            while(root != null)
            {
                Console.Write(String.Format("{0} ", root.Value));
                root = root.Child;
            }

            Console.WriteLine();
        }