C# Delegates Real World Usage [duplicate] - c#

This question already has answers here:
Where do I use delegates? [closed]
(8 answers)
Closed 9 years ago.
I've previously asked a question of about Delegates does anyone have a must have scenario where I would have to use a delegate? How does this improve my C# code?
Just as many scenarios I use it in I've always seem to be able to program around it.

Whenever you're using a Strategy Pattern or an Observer Pattern, delegates make your work much easier than using interfaces.

Nobody mentioned this, but if you are using LINQ with Lambda you use anonymous methods all the time. Which are technically still delegates.
Lets say you have a class called Person
class Person
{
public string FirstName { get; set; }
public string LastName { get; set; }
}
And you wanted to implement a find method where you would find the person based on their FirstName
public Person Where(List<Person> list, string firstName)
{
//find the string
foreach(Person item in list)
if(item.FirstName.Equals(firstName))
return item;
}
This is a very specific search and not very dynamic, meaning if you wanted to search by LastName you would have to change this method or write a new one.
Luckily LINQ provides an extension method called Where to which you need to pass a delegate, which you can create on the fly with the help of anonymous methods.
for instance
string searchString = "Stan";
list.Where( person => person.FirstName.Equals(searchString));
but if you wanted to change to search by LastName you would simply do this
string searchString = "R";
list.Where( person => person.LastName.Equals(searchString));
This example might be not what you were looking for, but I just wanted to show that sometimes we use delegates all the time without thinking about it or realizing it.

Assuming you're not talking about events - of course you can program around it. The point is to make it nicer and cleaner.
protected void Sort()
{
foreach (string key in _dBase.Keys)
{
Array.Sort<Pair<string, Dictionary<string, T>>>(_dBase[key],
new Comparison<Pair<string, Dictionary<string, T>>>(
delegate(Pair<string, Dictionary<string, T>> a, Pair<string, Dictionary<string, T>> b)
{
if (a == null && b != null)
return 1;
else if (a != null && b == null)
return -1;
else if (a == null && b == null)
return 0;
else
return a.First.CompareTo(b.First);
}));
}
}
Could I do that without an inline delegate? Sure. Would I have a floppy private method in my class that would only be used for this one instance? Yup.
Edit: As mentioned in the comments, you can simplify:
Array.Sort<Pair<string, Dictionary<string, T>>>(_dBase[key],
new Comparison<Pair<string, Dictionary<string, T>>>(
delegate(Pair<string, Dictionary<string, T>> a, Pair<string, Dictionary<string, T>> b)
{
to
Array.Sort<Pair<string, Dictionary<string, T>>>(_dBase[key], (a,b) =>
{

If you imagine C# without delegates, you would commonly encounter situations where you have classes or interfaces with one method. The name of that method is redundant. e.g.
public interface IGetMail
{
Mail JustGetTheMail();
}
The interface is all about that one method. A reference to an object of that type is really no more than a reference to a single callable method. The calling code:
Mail m = getMail.JustGetTheMail();
could be abreviated to:
Mail m = getMail();
The compiler could do that as "syntactic sugar" without any ambiguity, because there's only one method you could possible call on that getMail reference.
So let's add that feature to our C# compiler. Now, when declaring these types, we could make that a little neater as well. We don't need to specify the method name when calling it, so why should we have to give the method a name in the first place?
Let's pick a standard method name, Invoke, i.e.
public interface IGetMail
{
Mail Invoke();
}
We'll add some more syntactic sugar to allow us to write that as:
public delegate Mail GetMail();
Hey presto. We've added delegates to our C# compiler.
(Technically the CLR is also aware of delegates, and so rather than generating an interface, the C# compiler generates a special "delegate" type, which has support for asynchronous invocation, and manipulating an immutable list of delegates and treating them as a single reference; but in a basic form it could have been done with interfaces. There is a proposal to do that for Java).
We can then go further and add anonymous delegates - making them succinct to implement in a way that interfaces are not.
So to answer your question - any time where your interface has one method, it could be a delegate, and you'll be able to seriously cut down the amount of junk code you have to write.

Real World Usage:
Assume you have a simple user control called Checker- which comprises of just 2 checkboxes - chkA and chkB.
Within the user-control you can control the check/uncheck events by implementing the respective events fro chkA and ChkB
3.Now, in a new Win Form , when you drag in Checker...and your objective is to make sure that when chkA is clicked you have to change the background color of a label...lblColorPicker.
Mind you lblColorPicker is a control that exists in the form and is not directly bound to Checker.
How will you achieve this?
Answer:
First, you have to create a new event for your user control Checker.
To create this new event the first thing would be to create a delegate in you user control and then use this delegate as a defining type for the new event you are writing.
And then this Event has to be mapped to chkA...event in your user control.
This way you can control chkA...through the new event from any new form by referencing the event...through a delegate you just wrote.
So, much for Real-World usage!
This objective CANNOT be achieved with out writing the delegate.
Let me know if you think otherwise...or if you need more elaboration.

Anonymous delegates make the code much more readable in some case (you don't have to go to another method to see code that belongs to your method:
Winforms example
class MyForm:Form{
//...
protected override void OnLoad(EventArg e){
this.Cursor=Cursors.Wait();
this.Enabled=false;
// do a long running DB operation without blocking the UI Thread
ThreadPool.QueueUserWorkItem(state=>{
DoLongDBOperation();
// re enable the form
BeginInvoke(new Action(()=>{ this.Cursor=Cursors.Default;this.Enabled=true;}));
});
}

Delegates are an absolute must-have if you add events to your class or are doing anything asynchroneous (There are several other good reasons to have delegates). Benefits is that it is a very flexible approach.

I think you are referring to defining custom delegates?
EventHandler has minimised the requirement for custom delegate definitions but they are still useful if you want to add additional parameters to the method signature.

Whenever you need to modify or change any properties of a winForms control, you need to use a delegate to pass control back to the thread the control was created on... to name just one of many examples.

One example would be a pub/sub message dispatcher. You would need to register the events with the dispatcher and then call them appropriately. This allows you to connect disparate pieces of your code quite easily. I can't think of a way to do this without using delegates

Say you have a console application that responds to different key presses:
Action a = () => {/* Do Stuff*/};
Action b = () => {/* Do Stuff*/};
Action c = () => {/* Do Stuff*/};
Action d = () => {/* Do Stuff*/};
Action e = () => {/* Do Stuff*/};
Action f = () => {/* Do Stuff*/};
Action g = () => {/* Do Stuff*/};
Action h = () => {/* Do Stuff*/};
Action i = () => {/* Do Stuff*/};
Action j = () => {/* Do Stuff*/};
List<Action> actions = new List<Action>() {a,b,c,d,e,f,g,h,i,j};
string line;
while((line = Console.ReadKey().KeyChar) != 'q')
{
if(line.isBetween_0_and_9())
{
actions[line.ParseInt()]();
}
}
You can obviously just use a bunch of Ifs but this not only easier but it's almost certainly more clear/readable.

Related

Why does C# compiler create private DisplayClass when using LINQ method Any() and how can I avoid it?

I have this code (the whole code is not important but can be seen on this link):
internal static class PlayCardActionValidator
{
public static bool CanPlayCard(...)
{
// ...
var hasBigger =
playerCards.Any(
c => c.Suit == otherPlayerCard.Suit
&& c.GetValue() > otherPlayerCard.GetValue());
// ...
}
}
After opening the code in decompiler (ILSpy) for example I noticed the existence of newly created class <>c__DisplayClass0_0 by the C# compiler:
This wouldn't be a problem for me if this code wasn't critical for the performance of the system. This method is called millions of times and the garbage collector is cleaning these <>c__DisplayClass0_0 instances which slows down the performance:
How can I avoid creating this class (his instances and their garbage collecting) when using the Any method?
Why does the C# compiler create this class and is there any alternative of Any() I can use?
To understand the "display class" you have to understand closures. The lambda you pass here is a closure, a special type of method that magically drags in state from the scope of the method it's in and "closes around" it.
...except of course that there's no such thing as magic. All that state has to actually live somewhere real, somewhere that's associated with the closure method and readily available from it. And what do you call the programming pattern where you associate state directly with one or more methods?
That's right: classes. The compiler transforms the lambda into a closure class, then instantiates the class inside the hosting method so the hosting method can access the state in the class.
The only way to not have this happen is to not use closures. If this is really impacting performance, use an old-school FOR loop instead of a LINQ expression.
How can I avoid creating this class (his instances and their garbage collecting) when using the Any method?
Why does the C# compiler creates this class and is there any alternative of Any() I can use?
Other posters already explained the why part, so the better question would be How can I avoid creation of a closure?. And the answer is simple: if lambda is using only the passed parameters and/or constants, the compiler will not create a closure. For instance:
bool AnyClub() { return playerCards.Any(c => c.Suit == CardSuit.Club); }
bool AnyOf(CardSuit suit) { return playerCards.Any(c => c.Suit == suit); }
The first will not create a closure while the second will.
With all that in mind, and assuming you don't want to use for/foreach loops, you can create own extension methods similar to those in System.Linq.Enumerable but with additional parameters. For this particular case, something like this would work:
public static class Extensions
{
public static bool Any<T, TArg>(this IEnumerable<T> source, TArg arg, Func<T, TArg, bool> predicate)
{
foreach (var item in source)
if (predicate(item, arg)) return true;
return false;
}
}
and change the code in question to:
var hasBigger =
playerCards.Any(otherPlayerCard,
(c, opc) => c.Suit == opc.Suit
&& c.GetValue() > opc.GetValue());

How to identify a lambda closure with reflection

I am writing a component that involves Actions and came upon a requirement to find a way to identify using reflection cases when the Action.Target object is a closure that the compiler have generated. I am doing an experiment to try and find a way, the purpose of this little experiment is to develop a predicate that takes an Action and returns a bool that tells if the action target is an instance of such closure class.
In my test case, I have the following methods that create 4 different types of actions:
private void _createClosure(int i)
{
ClosureAction = new Action(() =>
{
var j = i;
var k = somenum;
});
}
private void _createLambda()
{
LambdaAction = new Action(() =>
{
this._instanceAction();
});
}
private void _createInstance()
{
InstanceAction = new Action(_instanceAction);
}
private void _createStatic()
{
StaticAction = new Action(_staticAction);
}
private int somenum;
private void _instanceAction()
{
somenum++;
}
private static void _staticAction()
{
}
The following table shows the properties of each action:
As you see, LambaAction and ClosureAction are quite similar in terms of defnition, they both use lambda, but the closure one has a local function variable that is being used inside the lambda, and therefore the compiler is forced into generating a closure class. Its clear that the second row, the one that presents ClosureAction, is the only one that has a target that is a closure type. The static one does not have a target at all, and the other two use the calling class (Called ActionReferences) as target. The next table presents a comparison of the target reflection type properties:
So we can see that what's unique about the closure case is that the target type is not a type info but rather a nested type. It's also the only one that is private nested, sealed and has a name that contains the string +<>c__DisplayClass. Now while I think that these characteristics are conclusive for any normal usage case, I would prefer to define a predicate that I can rely on. I don't like to base this mechanism on compilers naming conventions or properties that are not unique because technically, the user may create a private nested sealed class with the same naming convention... it's not likely, but it's not 100% clean solution.
So finally - the question is this: Is there a clean cut way to write a predicate the identifies actions that are actually compiler generated closures?
Thanks
This isn't 100% accurate, but it generally works:
bool isClosure = action.Target != null && Attribute.IsDefined(
action.Target.GetType(), typeof(CompilerGeneratedAttribute));
Console.WriteLine(isClosure);
You can of course force false positives just by manually adding [CompilerGenerated] to any type you choose.
You could also use action.Method.DeclaringType, but since all captures involve a target instance, it is useful to retain the Target check:
bool isClosure = action.Target != null && Attribute.IsDefined(
action.Method.DeclaringType, typeof(CompilerGeneratedAttribute));

C# syntax, assign delegate to a class, and call later

I have a bit of confusion with this C# syntax.
I'm trying to assign an arbitrary delegate to a class.
I have a delegates defined as
delegate string stringCB(string s);
delegate int intCB(int i);
I have a class
class run_by_name {
public string name {get;set;}
public Delegate method {get;set;}
};
And I'm trying to instantiate it
run_by_name myfuc = new run_by_name(){
name = "my name",
method = new stringCB(string s) {
return " testing " + s;
};
};
I'm really not clear how to assign to a delegate when there's a return type. Also I'm not sure how to call that method later on syntactically.
Why I'm doing this? Well I'm just writing some code that follows a pattern I use in JS a lot for event handling, I'm just making an "object" I can assign arbitrary functions to for a generic event handler that's created rather than defined. (important)
Also, alternatives to using delegates are welcome. :)
EDIT: How I might use it later
I don't have that written yet but Im pretty sure I'll be doing this.
List<run_by_name> callbacks = new List<run_by_name>();
/* lets say this is initialized and filled at this point */
public object FindAndRunCallback(string Name, object input) {
foreach(var cb in callbacks) {
if( cb.name == Name )
return cb.method(input);
}
return null;
}
Here's the syntax you need to get your current code working:
method = new stringCB((string s) => {
return " testing " + s;
})
Or, using lambda expressions:
method = new stringCB(s =>" testing " + s)
You could later invoke the method like so:
string result = (string) myfuc.method.DynamicInvoke("hello");
Without knowing more about your use case, it's hard to recommend other approaches, but I'd recommend at least looking into the following:
Events: Your description sounds very close to the common pattern for events and event handlers in C#. Your event defines the delegate type that is used to handle it, and code elsewhere can subscribe to that event with methods that match that delegate type. By convention, people usually pass a sender object as the first parameter, and some strongly-typed EventArgs so that subscribers don't have to guess at what data is going to be available when the event fires.
Func<> and Action<> variants: As C# has evolved into a more functional language, programmers have trended away from using custom delegate types, and toward using the provided variants of Func<> and Action<>. Since the arguments are strongly-typed still, you get most of the advantages of a compiled language, but use a little "duck typing" for the actual function you pass around.
For example, you could give your class a generic type based on what types you expect your delegate to deal with:
class run_by_name<T> {
public string name {get;set;}
public Func<T, T> method {get;set;}
};
Then use it:
var myfuc = new run_by_name<string>{
name = "my name",
method = s =>" testing " + s
};
string result = myfuc.method("hello");
dynamic: This keyword allows you to late-bind actions on any object. You lose the advantages of a compiled language, but it improves interoperability with more dynamic languages immensely. For example, an object can be created via JSON, and you can access the properties on it without declaring a special type for that object, just like you can in Javascript.
For example, if you changed your method declaration to this:
public dynamic method {get;set;}
Then you could simply say:
string result = myfuc.method("hello");
You have seceral choices. the strinCB constructor expects a method, that takes a string parameter and returns a string. If you have an existing method, you can pass it's name to the constructor, or you can create an anonymous method wither by delegate syntax like this:
method = new stringCB(delegate(string s)
{
return " testing " + s;
})
Or using a lambda expression:
method = new stringCB(s =>
{
return " testing " + s;
})
Then you can call it like this: myfuc.method.DynamicInvoke(YourParameter);
Normally, calling a delegate's method is pretty easy like this:
Func<int, int, int> sum = (x, y) => x + y;
Console.WriteLine(sum(2,3)); // with the name of delegate
Console.WriteLine(sum.Invoke(2,3)); // or using Invoke method
But in this case, you need to use DynamicInvoke because the type of your property is Delegate.
Apart from that .NET Framework has some useful built-in delegate types, such as Func,Action and Predicate etc. You can use them instead of creating your own delegate as long as they satisfy your needs. For example in this case you can use a Func<string,string> instead of stringCB.

Creating an object via lambda factory vs direct "new Type()" syntax

For example, consider a utility class SerializableList:
public class SerializableList : List<ISerializable>
{
public T Add<T>(T item) where T : ISerializable
{
base.Add(item);
return item;
}
public T Add<T>(Func<T> factory) where T : ISerializable
{
var item = factory();
base.Add(item);
return item;
}
}
Usually I'd use it like this:
var serializableList = new SerializableList();
var item1 = serializableList.Add(new Class1());
var item2 = serializableList.Add(new Class2());
I could also have used it via factoring, like this:
var serializableList = new SerializableList();
var item1 = serializableList.Add(() => new Class1());
var item2 = serializableList.Add(() => new Class2());
The second approach appears to be a preferred usage pattern, as I've been lately noticing on SO. Is it really so (and why, if yes) or is it just a matter of taste?
Given your example, the factory method is silly. Unless the callee requires the ability to control the point of instantiation, instantiate multiple instances, or lazy evaluation, it's just useless overhead.
The compiler will not be able to optimize out delegate creation.
To reference the examples of using the factory syntax that you gave in comments on the question. Both examples are trying (albeit poorly) to provide guaranteed cleanup of the instances.
If you consider a using statement:
using (var x = new Something()) { }
The naive implementation would be:
var x = new Something();
try
{
}
finally
{
if ((x != null) && (x is IDisposable))
((IDisposable)x).Dispose();
}
The problem with this code is that it is possible for an exception to occur after the assignment of x, but before the try block is entered. If this happens, x will not be properly disposed, because the finally block will not execute. To deal with this, the code for a using statement will actually be something more like:
Something x = null;
try
{
x = new Something();
}
finally
{
if ((x != null) && (x is IDisposable))
((IDisposable)x).Dispose();
}
Both of the examples that you reference using factory parameters are attempting to deal with this same issue. Passing a factory allows for the instance to be instantiated within the guarded block. Passing the instance directly allows for the possibility of something to go wrong along the way and not have Dispose() called.
In those cases, passing the factory parameter makes sense.
Caching
In the example you have provided it does not make sense as others have pointed out. Instead I will give you another example,
public class MyClass{
public MyClass(string file){
// load a huge file
// do lots of computing...
// then store results...
}
}
private ConcurrentDictionary<string,MyClass> Cache = new ....
public MyClass GetCachedItem(string key){
return Cache.GetOrAdd(key, k => new MyClass(key));
}
In above example, let's say we are loading a big file and we are calculating something and we are interested in end result of that calculation. To speedup my access, when I try to load files through Cache, Cache will return me cached entry if it has it, only when cache does not find the item, it will call the Factory method, and create new instance of MyClass.
So you are reading files many times, but you are only creating instance of class that holds data just once. This pattern is only useful for caching purpose.
But if you are not caching, and every iteration requires to call new operator, then it makes no sense to use factory pattern at all.
Alternate Error Object or Error Logging
For some reason, if creation fails, List can create an error object, for example,
T defaultObject = ....
public T Add<T>(Func<T> factory) where T : ISerializable
{
T item;
try{
item = factory();
}catch(ex){
Log(ex);
item = defaultObject;
}
base.Add(item);
return item;
}
In this example, you can monitor factory if it generates an exception while creating new object, and when that happens, you Log the error, and return something else and keep some default value in list. I don't know what will be practical use of this, but Error Logging sounds better candidate here.
No, there's no general preference of passing the factory instead of the value. However, in very particular situations, you will prefer to pass the factory method instead of the value.
Think about it:
What's the difference between passing the parameter as a value, or
passing it as a factory method (e.g. using Func<T>)?
Answer is simple: order of execution.
In the first case, you need to pass the value, so you must obtain it before calling the target method.
In the second case, you can postpone the value creation/calculation/obtaining till it's needed by the target method.
Why would you want to postpone the value creation/calculation/obtaining? obvious things come to mind:
Processor-intensive or memory-intensive creation of the value, that you want to happen only in case the value is really needed (on-demand). This is Lazy loading then.
If the value creation depends on parameters that are accessible by the target method but not from outside of it. So, you would pass Func<T, T> instead of Func<T>.
The question compares methods with different purposes. The second one should be named CreateAndAdd<T>(Func<T> factory).
So depending what functionality is required, should be used one or another method.

Need help to understand this piece of code in MVCContrib Grid

I'm a bit new to the concept of "Action" in C# and delegate in general.
I'm trying to study how to build a custom html component in MVC, and I chose the grid component of MVCContrib to start.
To add columns, typically we do
<%= Html.Grid(Model).Columns(column =>
{
column.For(model => model.Date).Format("{0:d}");
column.For(model => model.DayAmount);
column.For(model => model.LeaveType);
})
%>
and I see the source of Columns like the following
public IGridWithOptions<T> Columns(Action<ColumnBuilder<T>> columnBuilder)
{
var builder = new ColumnBuilder<T>();
columnBuilder(builder);
foreach (var column in builder)
{
if (column.Position == null)
{
_gridModel.Columns.Add(column);
}
else
{
_gridModel.Columns.Insert(column.Position.Value, column);
}
}
return this;
}
What I'm confused of is the Action parameter In this instance, Type is CustomBuilder, so when did the "CustomBuilder" object got instantiated?
I suppose, i can rewrite the calling statement above as
Html.Grid(Model).Columns(delegate(CustomBuilder<T> column)
{
});
or a bit more explicit as
Html.Grid(Model).Columns(new Action<CustomBuilder<T>>(delegate(CustomBuilder<T> column)
{
});
);
So are we saying, when the Action was instantiated with the "new" keyword above, the param "CustomBuilder" was instantiated as well?
Lastly, in the
"public IGridWithOptions<T> Columns(Action<ColumnBuilder<T>> columnBuilder)"
function,
the first two lines are
var builder = new ColumnBuilder<T>();
columnBuilder(builder);
What do they do? Looks like it's instantiating ColumBuilder object and pass it as a parameter to Action method columBuilder. Is this where you instantiate the parameter?
Thank you all.
It's nothing to do with action concept.
The delegates is present in .net from the beginning so you should start with the first step. Should build the wall before the roof.
Delegates
Lambda Expressions
Expression trees
But you should know about generic classes and methods, extension methods...
Got it after read this excellent article.
http://www.codeproject.com/Articles/47887/C-Delegates-Anonymous-Methods-and-Lambda-Expressio
while it's talking about Func, the concept applies to Action, which does not return any results.
Looks like the magic happens here
var builder = new ColumnBuilder();
columnBuilder(builder);
I obviously didn't understand the fact that delegate, is just a pointer to a function (anonymous or not). You still need to supply the parameter when calling it. (Duh!).
All cleared up now.
Thank you.

Categories

Resources