[英]C# raising events
I've been working a lot with C# recently, and I've noticed that most code that raises events in my company's code is done like this: 我最近一直在使用C#工作,我注意到在我公司的代码中引发事件的大多数代码都是这样完成的:
EventHandler handler = Initialized;
if (handler != null)
{
handler(this, new EventArgs());
}
I really don't understand why, instead, you can't do just do that: 我真的不明白为什么相反,你不能这样做:
if (Initialized != null)
{
Initialized(this, new EventArgs());
}
EDIT: 编辑:
Some food for thought, I tried doing a few tests on this: 有些值得深思,我试着对此做一些测试:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
Test t = new Test(true);
while(true)
{
t.Ev += new EventHandler(t_Ev);
t.Ev -= new EventHandler(t_Ev);
}
}
static void t_Ev(object sender, EventArgs e)
{
}
}
public class Test
{
private readonly bool m_safe;
public Test(bool safe)
{
m_safe = safe;
Thread t = new Thread(Go);
t.Start();
}
private void Go()
{
while (true)
{
if(m_safe)
{
RaiseSafe();
}
else
{
RaiseUnsafe();
}
}
}
public event EventHandler Ev;
public void RaiseUnsafe()
{
if(Ev != null)
{
Ev(this, EventArgs.Empty);
}
}
public void RaiseSafe()
{
EventHandler del = Ev;
if (del != null)
{
del(this, EventArgs.Empty);
}
}
}
}
The Unsafe version makes the program crash. 不安全版本会导致程序崩溃。
The first version is an attempt to make the event thread-safe . 第一个版本是尝试使事件成为线程安全的 。
See C# Events and Thread Safety 请参阅C#事件和线程安全
Actually, as said in the discussion, it doesn't make the event thread safe. 实际上,正如在讨论中所说,它不会使事件线程安全。 Thus I would use the second version that is shorter instead. 因此我会使用更短的第二个版本。
EDIT: event thread-safety is really hard to implement. 编辑:事件线程安全真的很难实现。 Look at what it might look ... If you're not actually dealing with multiple threads that register/unregister events, you shouldn't waste time with thread-safety. 看看它的外观 ......如果你实际上并没有处理多个注册/取消注册事件的线程,你就不应该浪费时间来保证线程安全。
The second version is not thread-safe. 第二个版本不是线程安全的。
if (Initialized != null)
{
Initialized(this, new EventArgs());
}
If the last handler unsubscribes after the if (Initialized != null)
then you will end up with null ref exception. 如果最后一个处理程序在if (Initialized != null)
之后取消订阅,那么最终会出现null ref异常。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.