O que esta chamada de delegado está fazendo nesta linha de código (C#)?
Pergunta
Isto é de um exemplo que acompanha o assembly agsXMPP .Net.Eu li sobre delegados, mas não tenho certeza de como isso se encaixa nessa linha de código (que aguarda a ocorrência do logon e depois envia uma mensagem.Acho que o que estou procurando é uma compreensão do porquê delegate(0)
consegue isso, em termos simples que posso entender.
xmpp.OnLogin += delegate(object o) {
xmpp.Send(new Message(new Jid(JID_RECEIVER),
MessageType.chat,
"Hello, how are you?"));
};
Solução
O delegate(object o){..}
diz ao compilador para empacotar tudo o que estiver entre colchetes como um objeto a ser executado posteriormente, neste caso quando OnLogin
é demitido.Sem o delegate()
instrução, o compilador pensaria que você está tentando executar uma ação no meio de uma instrução de atribuição e geraria erros.
Outras dicas
É exatamente o mesmo que
xmpp.OnLogin += EventHandler(MyMethod);
Onde está meu método
public void MyMethod(object o)
{
xmpp.Send(new Message(new Jid(JID_RECEIVER), MessageType.chat, "Hello, how are you?"));
}
Como observou Abe, esse código está criando uma função anônima.Esse:
xmpp.OnLogin += delegate(object o)
{
xmpp.Send(
new Message(new Jid(JID_RECEIVER), MessageType.chat, "Hello, how are you?"));
};
teria sido realizado da seguinte maneira em versões mais antigas do .Net (excluí declarações de classe e coisas assim, e apenas mantive os elementos essenciais):
delegate void OnLoginEventHandler(object o);
public void MyLoginEventHandler(object o)
{
xmpp.Send(
new Message(new Jid(JID_RECEIVER), MessageType.chat, "Hello, how are you?"));
}
[...]
xmpp.OnLogin += new OnLoginEventHandler(MyLoginEventHandler);
O que você está fazendo em ambos os casos é associar um método seu para ser executado quando o evento xmpp OnLogin for acionado.
OnLogin
no xmpp é provavelmente um evento declarado assim:
public event LoginEventHandler OnLogin;
onde LoginEventHandler
é um tipo de delegado provavelmente declarado como:
public delegate void LoginEventHandler(Object o);
Isso significa que para se inscrever no evento, você precisa fornecer um método (ou um método anônimo / expressão lambda) que correspondem ao LoginEventHandler
assinatura do delegado.
No seu exemplo, você passa um método anônimo usando o delegate
palavra-chave:
xmpp.OnLogin += delegate(object o)
{
xmpp.Send(new Message(new Jid(JID_RECEIVER),
MessageType.chat,
"Hello, how are you?"));
};
O método anônimo corresponde à assinatura do delegado esperada pelo OnLogin
evento (tipo de retorno void + um argumento de objeto).Você também pode remover o object o
parâmetro aproveitando o contravariância, já que não é usado dentro do corpo do método anônimo.
xmpp.OnLogin += delegate
{
xmpp.Send(new Message(new Jid(JID_RECEIVER),
MessageType.chat,
"Hello, how are you?"));
};
Isso está criando uma função anônima.Este recurso foi introduzido no C# 2.0
Ele serve como um método anônimo, portanto você não precisa declará-lo em outro lugar.É muito útil.
O que ele faz nesse caso é anexar esse método à lista de ações que são acionadas devido ao onLogin
evento.
Concordo com Abe, este é um método anônimo.Um método anônimo é apenas isso - um método sem nome, que pode ser fornecido como argumento de parâmetro.
Obviamente o objeto OnLogin é um Evento;usar um operador += garante que o método especificado pelo delegado anônimo acima seja executado sempre que o evento OnLogin for gerado.
Basicamente, o código dentro de {} será executado quando o evento "OnLogin" do evento xmpp for acionado.Com base no nome, acho que esse evento é acionado em algum momento durante o processo de login.
A sintaxe:
delegate(object o) { statements; }
é chamado de método anônimo.O código da sua pergunta seria equivalente a isto:
public class MyClass
{
private XMPPObjectType xmpp;
public void Main()
{
xmpp.OnLogin += MyMethod;
}
private void MyMethod(object o)
{
xmpp.Send(new Message(new Jid(JID_RECEIVER), MessageType.chat, "Hello, how are you?"));
}
}
Você está se inscrevendo no evento OnLogin no xmpp.
Isso significa que quando o xmpp dispara esse evento, o código dentro do delegado anônimo será acionado.É uma maneira elegante de receber retornos de chamada.
No Xmpp, algo assim está acontecendo:
// Check to see if we should fire the login event
// ALso check to see if anything is subscribed to OnLogin
// (It will be null otherwise)
if (loggedIn && OnLogin != null)
{
// Anyone subscribed will now receive the event.
OnLogin(this);
}