我想知道使用委托方法和使用常规方法[无代表]之间的区别。
使用代理:
delegate void DelMethod(string str);
static void Method(string str)
{
Debug.WriteLine(str);
}
用法:
DelMethod dm = new DelMethod(Method);
dm(string);
没有代表:
static void Method(string str)
{
Debug.WriteLine(str);
}
用法:
Method(string)
这两个有什么不同?
没有委托的方法更小更容易。但我发现编码员经常使用委托方法。
这背后的原因是什么?
答案 0 :(得分:18)
想象一下您有一个搜索客户的功能的场景。最初你只想按名称搜索,所以你写了类似的东西:
public Customer Find(string name)
{
foreach (var customer in database.Customers)
if (customer.Name == name)
return customer;
}
然后您的规格发生变化,您必须实施新的搜索方式(比如说“按地址搜索”)。没问题,我们将旧代码重构为:
public Customer FindByName(string name)
{
foreach (var customer in database.Customers)
if (customer.Name == name)
return customer;
}
public Customer FindByAddress(string address)
{
foreach (var customer in database.Customers)
if (customer.Address == address)
return customer;
}
他们看起来非常相似,不是吗?
现在,您的老板再次告诉您添加其他搜索功能,用户可能希望通过电话号码查找客户。它变得无聊,不是吗?
幸运的是,开发人员已经找到了一种方法,可以让其他开发人员更轻松地发明代理。使用它们可以创建一个更大的通用函数,帮助您避免一次又一次地重写相同的代码片段。
public Customer Find(Predicate<Customer> p)
{
foreach (var customer in database.Customers)
if (p(customer))
return customer;
}
现在,每次您需要一种新的搜索方式时,您都不必创建专门的功能,因此您可以写下:
var byName = Find(a => a.Name == "lorem");
var byAddress = Find(a => a.Address == "ipsum");
var byTelephone = Find(a => a.Telephone == "dolor");
委托对管理事件也很有用,并且在LINQ中也得到了密集使用。只需google“委托c#”,你就会发现一个巨大的新世界! :)
答案 1 :(得分:3)
代表们是另一种情况。想象一下,你有一个班级应该回答另一个班级的事情,但你对第二个班级一无所知。在这种情况下,您可以在第一个中执行委托。
// class where you know something
class A
{
//delegate for answer
public Func<bool> AskForSomething { get; set; }
public void DoSomething()
{
//some code
if(AskForSomething())
{
//do something
}
else
{
//do something else
}
}
}
class B
{
public void Test()
{
A a = new A();
a.AskForSomething = new Func<bool>(Answer);
a.DoSomething();
}
private bool Answer()
{
return true;
}
}
Class A
对class B
一无所知,但它可以调用B的方法并获得结果。 Answer
中的class B
方法私有,而class A
无法直接调用它。
在MSDN
中了解详情答案 2 :(得分:2)
代表的另一种用法:
如果没有委托,只有定义私有方法的类才能调用这些方法。通过在委托中包装方法,您可以将委托实例传递给其他类,并让它们使用适当的参数调用委托(作为回调),并最终在定义类中调用您的实际私有方法。
例如:
namespace DelegatesSample
{
public delegate void privateCallbackDelegate(string param1, int param2);
public class A
{
private void DelegatedMehod(string param1, int param2)
{
//Code for some action
}
private void CallBusinessClass()
{
privateCallBackDelegate del = new privateCallBackDelegate(DelegateMethod);
B b = new B();
b.InvokeBusinessMethod(del);
}
}
public class B
{
public void InvokeBusinessMethod(privateCallbackDelegate d)
{
//Do Some calculations and when finished, call the callback delegate
d("Done", result); //or d.Invoke or d.BeginInvoke
}
}
}
一般情况下,MSDN会在This article处发言:
代表在以下情况下非常有用:
答案 3 :(得分:1)
有一种特殊的情况,两个调用会有所不同,即涉及可选参数。考虑这些
delegate void DelMethod(string str = "hai");
static void Method(string str = "bye")
{
Debug.WriteLine(str);
}
DelMethod dm = Method;
dm();
//prints "hai"
但是
Method();
//prints "bye"
在第一种情况下,它是在调用站点插入的委托的可选参数。