Delegates To Lambdas Cheat Sheet

A cheat sheet Delegates & Lambdas in C#

All source code can be found on GitHub here.

This post is part of my cheat sheet series.

// DELEGATE DEFINITION
public delegate bool IsGreaterThan(int aParam, int compareTo);

// CREATION AND ASSIGNMENT

// .Net 1 version
IsGreaterThan isGreaterThanHandler = new IsGreaterThan(DelegatesToLambda.IsGreaterThanImplementation);

A cheat sheet for Ninject IOC Frmaework in C#

All source code can be found on GitHub <a href="https://github.com/lukewickstead/DOT-NET-on-Linux">here</a>.

// Method Group Conversion
IsGreaterThan isGreaterThanHandler = IsGreaterThanImplementation;

// Anonymous Function
IsGreaterThan isGreaterThanHandler = delegate(int aValue, int compareTo) { return aValue > compareTo; };

// Lambda Functions
IsGreaterThan isGreaterThanHandler = (int aValue, int compareTo) => { return aValue > compareTo; }; // Full hand
IsGreaterThan isGreaterThanHandler = (aValue, compareTo) => { return aValue > compareTo; }; // Param type inferrence
IsGreaterThan isGreaterThanHandler = (aValue, compareTo) => aValue > compareTo; // One line in method + return inferred
IsGreaterThan isGreaterThanHandler = aValue  => aValue > 1; // One param
IsGreaterThan isGreaterThanHandler = ()  => 2 > 1; // No params

// DELEGATES AND GENERICS

// Definition
public delegate string ConcatToString(T aValue, T compareTo);

// .Net 1 version
ConcatToString concatToStringHandler = new ConcatToString(DelegatesTestsWithGenerics.ConcatToStringImplementation);

// Method Group Conversion
ConcatToString concatToStringHandler = DelegatesTestsWithGenerics.ConcatToStringImplementation;

// Anonymous Function
ConcatToString concatToStringHandler = delegate(int aValue, int bValue) { return string.Format("{0}{1}", aValue, bValue); };

// Lambda Function
ConcatToString concatToStringHandle = (aValue, compareTo) => string.Format("{0}{1}", aValue, compareTo);

// FUNC<T, TResult>, ACTION PREDICATE

// Func, Action & Predicate are global delegates definitions to save creating your own.

// Func
// Func can take up to 16 parameter types and return one type

// Parameters expecting  a Func will looks something like
// Func
// Func<T, TResult>
// Func<T, T, TResult>
// Func<T, T, T, TResult>
// Func<T, T, T..... TResult>

Func<int, int, string> aHandler = delegate(int aInt, int bInt) { return string.Empty; }; // Anonymous Method
Func<int, int, string> cHandler = (anInt, anotherInt) => string.Empty; // Lambda

// Predicate can take up to 16 parameters and retun a bool
// Parameters expecting  a Predicate will looks something like
// Predicate<T, TResult>
// Predicate<T, T, TResult>
// Predicate<T, T, T, TResult>
// Predicate<T, T, T..... TResult>

Predicate aHandler = delegate(int anInt) { return anInt > 1; }; // Anonymous Method
Predicate cHandler = anInt => anInt > 1; // Lambda

// Action can take up to 16 parameters and retuns a null
// Parameters expecting  a Action will looks something like
// Predicate
// Predicate<T, T>
// Predicate<T, T, T>
// Predicate<T, T, T....., T>

Action aHandler = delegate(int x) { throw new Exception(); }; // Anonymous Method
Action bHandler = x => { throw new Exception(); };       // Lambda

// MULTICAST DELEGATES
// Multiple events can be registered and deregistered with += and -=
// All events are called one at a time.
// Last one returns the value.
IsGreaterThan isGreaterThanHandler = IsGreaterThanImplementation;
isGreaterThanHandler += IsGreaterOrEqual;
isGreaterThanHandler(1,2);
isGreaterThanHandler -= IsGreaterOrEqual;

// EVENTS
// Events are shorthand notation of grouping delegates
public delegate bool IsGreaterThan(int aParam, int compareTo);
public event IsGreaterThan IsGreaterThanEvent;
IsGreaterThanEvent += IsGreaterThanImplementation;
IsGreaterThanEvent += IsGreaterOrEqual;
IsGreaterThanEvent(1,2);
IsGreaterThanEvent -= IsGreaterOrEqual;

// CONTRAVARIANCE
Contravariance allows us to a method which has a parameter which is a child class of the defined parameter.

// COVARIANCE
Allows us to return a type which is a child class of the defined delegate return type

Advertisements

Day 13 – Delegates & Lambdas

The Source Code

This post is part of my Dot Net On Linux posts. All the source code is available on GitHub here

Intro

This post is just to point you to my How To on Delegates To Lambdas which can be found here and also to make the code available as part of the .Net on Linux post series.

Nothing to note really, everything I tried worked; from traditional delegates, method group conversion, anonymous delegates, lambdas, multicast delegates and the new Event keyword. All code can be available in the Git repo!

 

 

 

HowTo – Delegates to Lambdas

Source Code

All source code can be found on GitHub here.

My cheat sheet for Delegates can be found here.

This is part of my HowTo in .NET seriies. An overview can be seen here,

 

Intro

Delegates provide a type safe means of defining, assigning and calling methods when it is unknown which methods are to be called until runtime. It follows the Delegation design pattern where a task is delegated to another to perform.

Delegates provide the .NET way of writing the Observer design pattern which is also known as Listener, or Publish-Subscribe design patterns.

Examples of usage include events of  UI elements such as buttons, callbacks upon thread completions such as tasks or calling web services.

It is commonly used as a way to free up a resource or execute a command which was not known until runtime; aka asynchronous method invocation.

A delegate can point to nothing, a method or a list of methods all requiring notification of an event; multicasting or via multicastdelegates.

Delegates have changed their syntax through the versions of .NET, the hardest part of delegates comes from the numerous ways of writing them from initial delegates, method grouping, anonymous methods, lambdas and now events; even lambdas have various syntax notations to add to the complexity! However if you understand the rules, the versions of the syntax then you realise that each iteration of .NET has brought an easier way to write delegates!

Delegates can be split into three parts

  1. Delegate Definition
  2. Registration
    1. Original .net 1 egistration
    2. Method Groups invocation
    3. Anonymous Methods
    4. Lambdas
  3. Execution

Delegate Definition

The definition of the delegate is made up of three parts and is virtually the same as a method signature:

  1. Memory allocation.
  2. The parameter list (optional)
  3. The return type (can be null)

Take the following example:

public delegate bool IsGreaterThan(int aValue, int compareTo);

Notice the only difference to a method signature as found within an Interface is the keyword delegate and also a method accessor. Delegates can be static or instance variables and have any access modifier. The delegate definition defines the required method signature which is required for any listener to register to our broadcaster. If the listener tries to register with an incorrect method signature we will get a compile error.

Registration

Memory Allocation

We are initially going to look at how to implement delegates in .Net 1. The syntax has changed drastically through the .NET version iterations however we still need to understand how to write them in all possible ways; you might have to support or read code written in any one of them! Creating the memory allocation is as simple as creating a variable with the delegate definition as the type. For our example above our type is IsGreaterThan, we would therefore would write:

IsGreaterThan isGreaterThanHandler

Assignment Operator

Defined delegates all inherit from System.MulticastDelegate which in turn inherits from System.Delegate and provide us the ability to assign multiple events and to call them with one line of code. Like any reference type memory allocations, unless they are assigned they are initially null. We can assign methods to them with = or +=. Using = will change the contents of the delegate instance to be only the new method. Using += will add the method to the delegate instance allowing multiple methods to be registered; you can only perform += once an initial assignment has been made.

Assignment

We have already created a delegate definition which takes two ints as parameters and returns a bool. We need to assign a method which matches the same same signature; there are multiple ways we can do this, we will explore each syntax changes in the .NET version iterations.

Original ( .NET 1)

In our original orientation we need to start off writing the actual method we want to register to the delegate. This might sound a bit obvious however in later versions we don’t need to actually do this! Our method will need to match the delegate method signature above. We then create an instance of the delegate passing in the memory allocation of the method group of our require callback function, just like we were creating an instance of a reference type object! A method group is simply the method name without the brackets. If you have multiple overloads the compiler will pick the right one; remember delegates are type safe therefore the clever stuff happens at compile time!

public class DelegatesToLambda
{
	public delegate bool IsGreaterThan(int aValue, int compareTo);

	public static bool IsGreaterThanImplementation(int aValue, int compareTo)
	{
	    return aValue > compareTo;
	}

	public void Test01CreateADelegateInstance()
	{
	    IsGreaterThan isGreaterThanHandler = new IsGreaterThan(DelegatesToLambda.IsGreaterThanImplementation);
	}
}

In the example above we have a static method so we don’t need to create an instance of the class before hand. Also the accessor is public; there is nothing clever with delegates and access types; we still need to respect the law! In this example our code is all within the same class; our method could have been private, also we could access the function as if it was local.

IsGreaterThan isGreaterThanHandler = new IsGreaterThan(IsGreaterThanImplementation);

And yes we can also make use of the var keyword.

var isGreaterThanHandler = new IsGreaterThan(IsGreaterThanImplementation);

Method Group Conversion

We can actually do this:

IsGreaterThan isGreaterThanHandler = IsGreaterThanImplementation;

It is called method group conversion and as you have probably guessed the compile makes the MSIL create an instance of the delegates for us based upon our memory allocation. You can not use the var keyword here as it would not be able to infer which delegate type to use; the compiler is clever but not a mind reader!

Anonymous Methods

Anonymous Methods provide us a way to write the event method and create the delegate instance in-line of the assignment. When you use frameworks like Linq you end up writing a lot of little functions which only really have context in what you are currently doing and there is no real no benefit of having the method outside of that scope for reuse.

IsGreaterThan isGreaterThanHandler = delegate(int aValue, int compareTo) { return aValue > compareTo; };

Lambda Expressions

Lambda Expressions are a shorthand syntax of Anonymous Methods, as far as the runtime is concerned they are the same as the compiler generates the same MSIL. The above could be written with delegates as:

IsGreaterThan isGreaterThanHandler = (aValue, compareTo) => aValue > compareTo;

When compared to the Anonymous Method example we can see we have omitted the delegate keyword, the parameter types and the {} surrounding the method body. Depending upon the required method definition we could have omitted more, we could also have not omitted as much. The only difference we had to do to qualify as a Lambda was to remove the delegate keyword and enter the = >. Our example above could have been written as:

IsGreaterThan isGreaterThanHandler = (int aValue, int compareTo) => { return aValue > compareTo; }

This is probably a little more self explanatory from our current traversal of delegates from .NET 1. The syntax reads:Parameter List = > Method Body; Just like any method definition, which is what we are defining; we just have some syntax to shortcut writing the code. Lambdas themselves can take on multiple forms due to the possible short-cuts we can take with them.

  1. You can omit the parameter type in the parameter list as they can normally be worked out of ‘inferred’.
  2. If you have one line of code which returns a value  you can omit the {}.
  3. If you have one line of code and it returns a value you can omit the return keyword.
  4. If you have one parameter you can omit the () around the parameter list.
  5. If you have no parameters you use an empty ()

Below are some examples highlighting the previous points.

(int x) => { return x > 1; } // Full Lambda notation
x => x > 1; // Points 1,2,3,4
(int x) => return true; // Point 2
() => { int x = 1; return x > 1' } // Point 5
(x, y) => return x > y; // Point 1, 2

Execution

Executing or calling the registered delegate methods is the same as any other method except we use the memory allocation is the delegate instance

var isgreater = isGreaterThanHandler(1,2);

If we have multiple methods registered each one would be called in turn, however only the last registered method would be able to return its value. If you need the value you would need to loop through the delegates invocation list and call each method in turn.

foreach(aDel d in s.isGreaterThanHandler())
{
   var isgreater = d(1,2);
}

Un-Asign

We can then un-assign methods from the delegate instance to them with = null or -=. Using = null will remove all methods from the delegate instance. Using -= allows us to remove just one method though this will require us to keep a handle of the required delegate instance (which has only the method we are interested in ) and removing it from the delegate instance which contains all out methods; if you look at the original assignment we create an instance of a delegate method and then add more instances onto the original one. We can use the new event keyword which provides a little more sane syntax; this is described later on!

Delegate and Generics

We can also replace our types with generic implementations. This example shows string concatenation of two variables with type T along with all our previously mentioned ways of allocating methods.

public delegate string ConcatToString(T aValue, T compareTo);

public static string ConcatToStringImplementation(T aValue, T bValue)
{
    return string.Format("{0}{1}", aValue, bValue);
}

// Full delegate registration
var fullHandler = new ConcatToString(DelegatesTestsWithGenerics.ConcatToStringImplementation);

// Registration with method group conversion
var methodGrpHandler = DelegatesTestsWithGenerics.ConcatToStringImplementation;

// Registration with anonymous method.
var anonMethodHandler = delegate(int aValue, int bValue) { return string.Format("{0}{1}", aValue, bValue); };

// Registration with Lambda
var lambdaHandler = (aValue, compareTo) => string.Format("{0}{1}", aValue, compareTo);

Action, Func and Predicate

A delegate definition contains nothing more than the list of required parameters and the the return type. .Net provide three global delegates which are used extensively in frameworks such as Linq. Each one has numerous overloads; up to 16 different parameters with different types.

Func<T, TResult>: can take take up to 16 parameters and one return type.

Action<T>: can take up to 16 parameters and the return type of null.

Predicate<T> can take up to 16 parameters and return a type of bool.

Func<T>

// Parameters expecting  a Func will looks something like
// Func
// Func<T, TResult>
// Func<T, T, TResult>
// Func<T, T, T, TResult>
// Func<T, T, T..... TResult>

Func<int, int, string> aHandler = delegate(int aInt, int bInt) { return string.Empty; };
Func<int, int, string> bHandler = (anInt, anotherInt) => { return string.Empty; };
Func<int, int, string> cHandler = (anInt, anotherInt) => string.Empty;

Func dHandler = delegate() { return string.Empty; };
Func eHandler = () => string.Empty;

Predicate

// Parameters expecting  a Predicate will looks something like
// Predicate
// Predicate<T, T>
// Predicate<T, T, T>
// Predicate<T, T, T..... T>

Predicate aHandler = delegate(int anInt) { return anInt > 1; };
Predicate bHandler = delegate(int anInt) { return anInt > 1; };
Predicate cHandler = anInt => { return anInt > 1; };
Predicate dHandler = anInt => anInt > 1;

Action

// Parameters expecting  a Predicate will looks something like
// Action
// Action<T, T>
// Action<T, T, T>
// Action<T, T, T..... T>

Action aHandler = delegate(int x) { throw new Exception(); };
Action bHandler = delegate(int x) { throw new Exception(); };
Action cHandler = x => { throw new Exception(); };
// Action dHandler = x => throw new Exception();  // We don't return anything so we can not omit the {} around the method body

Contravariance

Contravariance allows us to call a delegate with a parameter which is of a child or inherited class. In many cases you don’t need to know about the parameters, only to trigger an event. This can save writing multiple delegates!


  public class ChildEventArgs : EventArgs
    {

    }

    public class ContravarianceExample
    {
        // Define the delegate.
        public delegate void RaiseEventWithEventArgs(object sender, EventArgs e);
        public delegate void RaiseEventWithChildEventArgs(object sender, ChildEventArgs e);

        public static void DoWithEventArgs(object sender, EventArgs e)
        {
        }

        public static void DoWithChildEventArgs(object sender, DataReceivedEventArgs e)
        {
        }

        public void TestCovariance()
        {
            RaiseEventWithChildEventArgs raiseEventWithChildEventArgs = DoWithEventArgs;
            raiseEventWithChildEventArgs(this, new ChildEventArgs());
        }
    }

Covariance

Covariance allows us to return a type which is a child of the defined return type of the delegate.

 // Define the delegate.
        public delegate Parent ReutrnParent();

        public static Parent ReturnParent()
        {
            return new Parent {ParentField = "A Parent!"};
        }

        public static Child ReturnChild()
        {
            return new Child { ChildField = "A Child!", ParentField = "A Parent!" };
        }

        public static void TestCovariance()
        {
            ReutrnParent returnParent = ReturnParent;

            var aParent = returnParent();

            // Covariance allows this delegate.
            ReutrnParent returnChild = ReturnChild;

            var aChild = returnChild() as Child;
        }

Multicast delegates and Events

We have mentioned previously that delegates are multicast. We can assign multiple event methods into the instance. During normal instantiation of delegates you create one. When you want to assign another you += another instance onto a previous one.

IsGreaterThan isGreaterThanHandler = IsGreaterThanImplementation;
isGreaterThanHandler += IsGreaterOrEqual;
isGreaterThanHandler(1,2) // execution

To remove a method you use the -= against the delegate instance which contains all methods and either the method group or the instance of the delegate you created.

IsGreaterThan isGreaterThanHandler = IsGreaterThanImplementation;
isGreaterThanHandler += IsGreaterOrEqual;
isGreaterThanHandler(1,2) // execution
isGreaterThanHandler -= IsGreaterOrEqual;

Events allow a common place holder for storing the event methods with functionality to call, add and remove methods without having to ‘keep a handle of the first instance’.

public delegate bool IsGreaterThan(int aValue, int compareTo);
public event IsGreaterThan IsGreaterThanEvent;
IsGreaterThanEvent += IsGreaterThanImplementation;
IsGreaterThanEvent += IsGreaterOrEqual;

IsGreaterThan isGreaterThanHandler = IsGreaterThanImplementation;
isGreaterThanHandler += IsGreaterOrEqual;
isGreaterThanHandler(1,2) // execution
isGreaterThanHandler -= IsGreaterOrEqual;

Day 11 – NInject

The Source Code

This post is part of my Dot Net On Linux posts. All the source code is available on GitHub here

Intro

NInject is a IOC framework for .Net and Mono. I had an initial investigation in a previous post here and also cheat sheet here.

I decided to do an API trawl to learn as much as possible about how to use the framework, the code associated with this post is my findings and the HowTo post can be found here and here.

The source code (see above) demonstrates examples of all functionality of the API which I can find, if you find anything missing please let me know!

Day 10 – Linq

The Source Code

This post is part of my Dot Net On Linux posts. All the source code is available on GitHub here

Intro

The Linq or Language Integrated Query is a framework or component which adds query functionality into the .Net framework.

I have a HowTo on Linq which can be found here.

You can also find my cheat sheets on Linq and Linq extensions.

Linq & Mono

Linq in C# and mono worked flawlessly. It is built into the core mono runtime library of System.Core which is the same as .Net.

The only point I would like to raise is VB.NET and Linq appears to be somewhat lacking. I tried to rewrite the code in VB.NET and I literally could not get anything to compile. I will be investigating shortly to see if I can take it any further and will report back shortly.

Day 9 – Generics

The Source Code

This post is part of my Dot Net On Linux posts. All the source code is available on GitHub here

Intro

Generics allow code to be come for “generic” by providing the ability to have parameter types as ‘type parameter’.

You can read more on my How To here.

You can also find my Generics Cheat Sheet here.

Code Examples

Mean Calculator

Probably not the best usage of generics but an example to calculate the mean average from any set of numbers

Enumerator or Number Parser

An example of how to parse any string to an Enumerator or Number with overrides to allow a default value when not passed, throw an exception or to return the types default value

Serialize and De-serialize any class to and from XML

An example of how to serialize and de-serialize any class to and from XML with one method call.

NInject Cheat Sheet

A cheat sheet for Ninject IOC Frmaework in C#

All source code can be found on GitHub here.

This post is part of my cheat sheet series.

You can also view my HowTos  here and here


// **** DETERMINING WHICH CONSTRUCTOR TO USE ****
// The main DI pattern is Constructor Injection
// A known constructor parameter is one which has been explicitly bound
// An unknown constructor parameter is one which has not been explicitly bound even if it has a resolvable constructor the following order defines which constructor is used
// 1. User defined costructor marked with [Inject] attribute
// 2. The constructor with the most known bound parameters.
// 3. The default parameterless constructor

// **** PROPERTY / METHOD INJECTION
// Properties and methods marked with the [Inject] property will be resolved imediatly after the selected constructor
// Properties are required to be public set and private get
// Methods should be public and return void

[Inject]
public void AMethod(IClass aClass)
{
    this.aClass = aClass;
}

[Inject]
public IClass Property { private get; set; }

// **** BIND TO ****
// Classes are automatically bound to themselves
Bind<IClass>().ToSelf( )			// Explicit self binding
Bind<IClass>().To<Class>();  			// Bind to class
Bind<IClass>().ToConstant( )			// Binding with constant (the returned class), implicitly sets scope to InSingletonScope
Bind<IClass>().ToConstructor( )			// Bind with constructor
Bind<IClass>().ToMethod( )			// Binding with method
Bind<IClass>().ToProvider( )			// Binding with provider, class with parent of Provider<T> allowing addressing of complex initiation

// **** BINDING SCOPE ****
// The lifetime of an instance can be defined via the scope of the binding
// The default scope is InTransientScope
kernel.Bind<IClassA>().To<B>(ClassA).InTransientScope()  	// Always create an instance per Get call
kernel.Bind<IClassA>().To<B>(ClassA).InSingletonScope()		// Create only one instance
kernel.Bind<IClassA>().To<B>(ClassA).InThreadScope()		// Create one instance per thread and always return this
kernel.Bind<IClassA>().To<B>(ClassA).InRequestScope()		// Create one instance per web request and return this
kernel.Bind<IClassA>().To<B>(ClassA).InScope(Func<object>)	// Returns an object associated with the lifetime. The same instances is returned for the same life time of this associated lifetime object. Once this has been garbage collected our bound object will be recreated

// **** CONDITIONAL BINDING ****
Bind<IClass>().To<Class>().Named("AName");  				// Named Binding
Bind<IClass>().To<Class>().WithConstructorArgument("Iclass", delegat/object); // Constructor Argument
Bind<IClass>().To<Class>().WithMetadata("AMetaName", false); 		// Derrived Attribute Bindings
Bind<IClass>().To<Class>().WithParameter(new ConstructorArgument/Property("IClass/PropertyName", new XYZ() ); // WithConstructorArgument is a short cut to this
Bind<IClass>().To<Class>().WithPropertyValue(ProprtyName, delegate/object); // Explicit property injection
Bind<IClass>().To<Class>().When();					// Explicit Conditional binding
Bind<IClass>().To<Class>().WhenAnyAnchestorNamed("AnyParentInAncestry"); // When any class in ancestry is named
Bind<IClass>().To<Class>().WhenClassHas<AnAttribute>();  		// Binding with attributes based helpers
Bind<IClass>().To<Class>().WhenInjectedInto(typeof(AClass)); 		// Conditional injected into AClass or any derrived classes
Bind<IClass>().To<Class>().WhenInjectedExactlyInto(typeof(AClass));	// Conditional injected into AClass and not any derrived classes
Bind<IClass>().To<Class>().WhenMemberHas<AnAttribute>();  		// Binding with attributes based helpers
Bind<IClass>().To<Class>().WhenParentNamed("ParentName");		// Bind when the direct parent is named
Bind<IClass>().To<Class>().WhenTargerHas<AnAttribute>(); 		// Binding with attributes based helpers

// **** MULTIPLE BINDING WITH BindingConfiguration ****
// Default bind up to 4 however more can be found via caching and provinding the bind config.
var bindingConfiguration =
    Bind<IInterface1, IInterface2, IInterface3, IInterface4>()
        .To<Implementation>()
        .BindingConfiguration;
kernel.AddBinding(new Binding(typeof(IInterface5), bindingConfiguration));
kernel.AddBinding(new Binding(typeof(IInterface6), bindingConfiguration));

// **** OnActivation AND OnDeactivation EVENTS
// Trigger evets on the activation and deactivation
Bind<IClass>().To<Class( ).OnActivation( x => x.ActivationMethod())		// Called when an object is activate (instantiated)
Bind<IClass>().To<Class( ).OnDeactivation(x => x.DeactivationMethod())		// Called when an object is deactivate (disposed?)

// **** KERNEL CREATION ****
IKernel kernel = new StandardKernel();

// *** KERNEL MODULES ***
// Provide a grouping of registring bindings
public class WarriorModule : NinjectModule
{
    public override void Load() { } 	// Binding code goes in here
    public override void OnLoad() { } 	// OnLoad event
    public override void OnUnLoad() { } // OnUnload event
}

IKernel kernel = new StandardKernel(new AKernelModule());
IKernel kernel = new StandardKernel(new Module1(), new Module2(), ...);
kernel.Load/UnLoad("*.dll"); // Load / Unload all Kernel Modules within dll
kernel.Load.UnLoad(AppDomain.CurrentDomain.GetAssemblies()); // // Load / Unload all Kernel Modules within the current domains dll's

// **** GET / RESOLVE / INJECT ****
// During execution of code request instance of injected class via the kerel
// Any classes passed in as parameters to the constructor or INJECT marked methods/properties will be automatically resolved.
var aClass = kernel.Get<IClass>();
var classes = kernel.Get<IWarrior>( new ConstructorArgument( "IClass", new AClass() ) );
var classes = kernel.GetAll<IClass>();

// **** MULTIPLE BINDINGS
public ClassName( IEnumerable<IClass> classes) // An instance off all classes implementing the interface will be injected in

// **** NAMED BINDING ****
Bind<IClass>().To<ClassA>().Named("First"); 	// Name the binding during binding
Bind<IClass>().To<ClassB>().Named("Second");
kernel.Get<IClass>("First"); 			// Resolve the bind by providing the name
public ClassC ( [Named("First") IClass aClass]  // Consuctors, Methods and Properties can have named parameters to resolve their injection

// **** DERRIVED ATTRIBUTE BINDINGS ****
// Define an attribute
[AttributeUsage(AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Parameter, AllowMultiple = true, Inherited = true)]
public class IsSomething : ConstraintAttribute {
    public bool Matches(IBindingMetadata metadata) {
        return metadata.Has("IsSomething") && metadata.Get<bool>("IsSomething");
    }
}

Bind<IClass>().To<AClass>().WithMetadata("IsSomething", false);
Bind<IClass>().To<BClass>().WithMetadata("IsSomething", true);

public AnotherClass([IsSomething] IClass aClass) {} // face resolves to BClass

// TODO: try this bit
kernel.Get<IClass>(metadata => metadata.Has("IsSomething") && metadata.Get<bool>("IsSomething") == false ) // resolves to AClass

// **** BINDING WITH ATTRIBUTE BASED HELPERS ****
// The Target: the parameter being injected into
// The Member: the property, method or constructor itself
// The Class: the class Type within which the Member or Target is defined within

[AttributeUsage(AttributeTargets.Class, AllowMultiple = true, Inherited = true)]
public class WhenClassHas : Attribute{ }

[AttributeUsage(AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Parameter, AllowMultiple = true, Inherited = true)]
public class WhenMemberHas : Attribute{}

[AttributeUsage(AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Parameter, AllowMultiple = true, Inherited = true)]
public class WhenTargetHas : Attribute{}

public class InjectWhenMemberAndTargetHas
{
	[Inject, WhenMemberHas]
	public IClass WhenMemberHas { get; set; } // Member has an attribute
	public IClass WhenTargetHas { get; set; }
	public InjectWhenMemberAndTargetHas([WhenTargetHas] IClass aClass){WhenTargetHas = aClass;} // target has an attribute
}

[WhenClassHas]
public class InjectWhenClassHas
{
	[Inject] // Class is marked with attriibute. binding is done by class
	public IClass WhenClassHas { get; set; }
}

Bind<IClass>().To<KnownC>().WhenClassHas<WhenClassHas>();
Bind<IClass>().To<KnownD>().WhenTargetHas<WhenTargetHas>();
Bind<IClass>().To<KnownE>().WhenMemberHas<WhenMemberHas>();

// **** BIND WITH METHOD ****
// Used to bind to factory methods.
// Here we are passing in the reques5 context tyoe
Bind<IClass>().ToMethod( context => AFactory.Create( context.Request.Target.Type ) )
Bind<IClass>().ToMethod( x => new ClassC(x.Kernel.Get<IClassA>(), x.Kernel.Get<IClassB>()));

// **** BIND TO PROVIDER ****
// Binding with provider, class with parent of Provider<T> allowing addressing of complex initiation
Bind<IClass>().ToProvider(new AProvider())

public class AProvider : Provider<AClass>
{
    protected override AClass CreateInstance(IContext context)
    {
        return new AClass(); // Do some complex initialization here.
    }
}

// **** BIND TO CONSTRUCTOR ****
Bind<IMyService>().ToConstructor( ctorArg => new ClassC(ctorArg.Inject<IClassA>(), ctorArg.Inject<IClassB>())); // TODO what is the difference between constructor and method binding

// **** BIND WITH CONSTRUCTOR ARGUMENT ****
Bind<IClass>().To<Class>().WithConstructorArgument("ParameterName", x =>x.Kernel.Get<IClass>()); //

// **** BIND WITH EXPLICIT CONDITIONAL BINDING ****
Bind<IClass>().To<ClassA>().When(request => request.Target.Member.Name.StartsWith("ClassName"));
Bind<IClass>().To<ClassB>().When(request => request.Target.Type.Namespace.StartsWith("NameSpace.ClassName"));