如何将对象投射到Action< T> [英] How to cast object to Action<T>
本文介绍了如何将对象投射到Action< T>的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!
问题描述
我已经创建了一个简单的消息总线,它可以排队并发出/发布事件.
I've created a simple message bus that queues and emits/publishes events.
我正在使用StructureMap定位事件的注册处理程序( Action< T>
),但不确定如何将其从StructureMap返回的对象强制转换为可调用的操作.
I'm using StructureMap to locate the registered handlers (Action<T>
) of the event but am not sure how to cast it from the object that StructureMap returns into an invoke-able action.
因为我无法转换为 Action< object>
,所以我假设 Action< T>
不是协变的?可以用另一种方式吗?
Since I can't cast to Action<object>
I'm assuming that Action<T>
is not covariant? Can this be done another way?
public class Bus
{
private ConcurrentQueue<object> events = new ConcurrentQueue<object>();
public void Queue<TEvent>(TEvent e)
{
events.Enqueue(e);
}
public void Emit()
{
object e;
while (events.TryDequeue(out e))
{
var handlerType = typeof(Action<>).MakeGenericType(e.GetType());
foreach (var handler in ObjectFactory.GetAllInstances(handlerType))
{
// how to invoke action?
}
}
}
}
推荐答案
如果在您的 Queue
方法内部,您不将事件排队,而是将发出事件的代码排队?
What if inside your Queue
method you'd queue not events but rather the code which emits them?
private ConcurrentQueue<Action> handlers = new ConcurrentQueue<Action>();
public void Queue<TEvent>(TEvent e)
{
handlers.Enqueue(new Action(() =>
{
foreach (var handler in GetHandlers<TEvent>())
{
handler(e);
}
}));
}
public void Emit()
{
Action act;
while (handlers.TryDequeue(out act))
{
act();
}
}
private IEnumerable<Action<TEvent>> GetHandlers<TEvent>()
{
return ObjectFactory.GetAllInstances(typeof(Action<TEvent>>));
}
希望这会有所帮助.
这篇关于如何将对象投射到Action< T>的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!
查看全文