Examples

The following example finds the intersection of two collections of System.Type objects. It uses the adapter functionality of the NstlUtil class to be able to use standard .NET collections from the System.Collections.Generic namespace.
using System;
using System.Collections.Generic;
using NStl;

namespace NstlExamples
{
    class A { }
    class B : A { }
    class C : A { }
    class D : B { }
    class E { }

    class LessByName<T> : BinaryPredicate<T, T>
    {
        bool BinaryFunction<T, T, bool>.Execute(T lhs, T rhs)
        {
            return lhs.ToString().CompareTo(rhs.ToString()) < 0;
        }
    }

    class Program
    {
        static void Main()
        {
            Type[] tps1 = new Type[] { typeof(A), typeof(B), typeof(E) };
            Type[] tps2 = new Type[] { typeof(A), typeof(B), typeof(D) };

            Algorithm.Sort(NstlUtil.Begin(tps1), NstlUtil.End(tps1),
                           new LessByName<Type>());
            Algorithm.Sort(NstlUtil.Begin(tps2), NstlUtil.End(tps2),
                           new LessByName<Type>());

            List<Type> result = new List<Type>();

            Algorithm.SetIntersection(NstlUtil.Begin(tps1), NstlUtil.End(tps1),
                     NstlUtil.Begin(tps2), NstlUtil.End(tps2),
                     NstlUtil.BackInserter(result), new LessByName<Type>());

        }
    }
}

The next code block does exactly the same as the first one. The difference is that instead of implementing a functor to compare two Types, it uses a anonymous delegate which is adapted by the Functional.PtrFun(...) method.
using System;
using System.Collections.Generic;
using NStl;

namespace NstlExamples
{
    class A { }
    class B : A { }
    class C : A { }
    class D : B { }
    class E { }

    class Program
    {
        static void Main()
        {
            BinaryFunction<Type, Type, bool> lessByName = 
                Functional.PtrFun<Type, Type, bool>(delegate(Type lhs, Type rhs){
                                        return lhs.ToString().CompareTo(rhs.ToString()) < 0;
                                                                                 });
            Type[] tps1 = new Type[] { typeof(A), typeof(B), typeof(E) };
            Type[] tps2 = new Type[] { typeof(A), typeof(B), typeof(D) };

            Algorithm.Sort(NstlUtil.Begin(tps1), NstlUtil.End(tps1), lessByName);
            Algorithm.Sort(NstlUtil.Begin(tps2), NstlUtil.End(tps2), lessByName);

            List<Type> result = new List<Type>();
            Algorithm.SetIntersection(NstlUtil.Begin(tps1), NstlUtil.End(tps1),
                     NstlUtil.Begin(tps2), NstlUtil.End(tps2),
                     NstlUtil.BackInserter(result), lessByName);

        }
    }
}

In the next example all values are extracted from a collection of key value pairs using the Algorithm.Transform algorithm and the Select.SecondFromKeyValuePair functor and inserted into a LinkedList.
using System.Collections.Generic;
using NStl;

namespace NstlExamples
{
    class Program
    {
        static void Main()
        {
            List<KeyValuePair<int, string>> int2str = new List<KeyValuePair<int, string>>();

            // … file the list
            for (int i = 0; i < 10; ++i)
                int2str.Add(new KeyValuePair<int, string>(i, i.ToString()));

            LinkedList<string> strs = new LinkedList<string>();

            Algorithm.Transform(NstlUtil.Begin(int2str), NstlUtil.End(int2str),
                NstlUtil.BackInserter(strs), Select.SecondFromKeyValuePair<int, string>());

        }
    }
}

In the next example the value of 10 is searched in a custom NSTL collection using an existing static function and the Algorithm.Find(...) linear search algorithm.
using System;
using NStl;

namespace NstlExamples
{
    class Program
    {
        static bool Equals10(int par)
        {
            return par == 10;
        }
        static void Main()
        {
            DList<int> ints = new DList<int>();
            for (int i = 0; i < 20; ++i)
                ints.PushBack(i);

            DList<int>.Iterator found = 
                Algorithm.FindIf(ints.Begin(), ints.End(), 
                            Functional.PtrFun<int, bool>(Equals10));

            if (!found.Equals(ints.End()))
                Console.WriteLine("Found value: " + found.Value.ToString());
        }
    }
}

The above sample can also be implemented without a custom function at all by using the provided binary function returned by the Compare.EqualTo<T>() factory method and a so called binder. The Bind.Second binder factory method returns an adapter object that will store the value of 10 and pass it as the second parameter into the EqualTo binary function for each item in the DList<T>.
using System;
using NStl;

namespace NstlExamples
{
    class Program
    {
        static void Main()
        {
            DList<int> ints = new DList<int>();
            for (int i = 0; i < 20; ++i)
                ints.PushBack(i);

            UnaryPredicate<int> equals10 = 
                Bind.Second(Compare.EqualTo<int>(), 10);
            
            DList<int>.Iterator found = 
                Algorithm.FindIf(ints.Begin(), ints.End(), equals10);

            if (!found.Equals(ints.End()))
                Console.WriteLine("Found value: " + found.Value.ToString());
        }
    }
}

It is possible to combine existing functors using the so called composition binders. Basically these are functors that execute a given functor and use the result as input for other functors. The following example evaluates as string property, converts the result to an integer and appends it to a target collection.
using System.Collections.Generic;
using NStl;

namespace NstlExamples
{
    class Something
    {
        public Something(string name)
        {
            this.name = name;
        }
        public string Name
        {
            get { return name; }
        }
        private readonly string name;
    }
    class Program
    {
        static void Main()
        {
            IList<Something> somethings = new List<Something>();
            for (int i = 0; i < 20; ++i)
                somethings.Add(new Something(i.ToString()));

            // ... evaluate string property
            UnaryFunction<Something, string> somethingsPropName =
                Functional.PtrFun<Something, string>(delegate(Something s) { return s.Name; });
            
            // ... convert a string to an integer
            UnaryFunction<string, int> convertToInt =
                Functional.PtrFun<string, int>(delegate(string s) { return int.Parse(s); });

            // ... combine both functors to convert the name property to an integer
            UnaryFunction<Something, int> somethingsName2Int =
                Compose.FGx(convertToInt, somethingsPropName);

            ICollection<int> namesAsInts = new LinkedList<int>();

            Algorithm.Transform(NstlUtil.Begin(somethings), NstlUtil.End(somethings), 
                                NstlUtil.BackInserter(namesAsInts), somethingsName2Int);
        }
    }
}

Last edited Jan 2, 2008 at 5:58 PM by AndyM, version 12

Comments

No comments yet.