Использование System.Threading.Timer
приводит к тому, что потоки запускаются из ThreadPool
, что означает, что интервал выполнения для таймера истекает, пока поток все еще обрабатывает по порядку предыдущего запроса, то тот же обратный вызов будет делегирован для выполнения в другом потоке. Это, очевидно, вызовет проблемы в большинстве случаев, если обратный вызов не будет знать о повторном входе, но мне интересно , как сделать это наилучшим (то есть безопасным) способом.
Допустим, у нас есть следующее:
ReaderWriterLockSlim OneAtATimeLocker = new ReaderWriterLockSlim();
OneAtATimeCallback = new TimerCallback(OnOneAtATimeTimerElapsed);
OneAtATimeTimer = new Timer(OneAtATimeCallback , null, 0, 1000);
Если весь шебанг будет заблокирован, как таковой:
private void OnOneAtATimeTimerElapsed(object state)
{
if (OneAtATimeLocker.TryEnterWriteLock(0))
{
//get real busy for two seconds or more
OneAtATimeLocker.ExitWriteLock();
}
}
Или следует управлять только входом и выгнать «нарушителей» как таковых: используется для регистрации контроллеров, теперь не рекомендуется:
public class WindsorControllerFactory : DefaultControllerFactory
{
IWindsorContainer container;
public WindsorControllerFactory()
{
container = new WindsorContainer(new XmlInterpreter(new ConfigResource("castle")));
// register all the controller types as transient
var controllerTypes = from t in Assembly.GetExecutingAssembly().GetTypes()
where typeof(IController).IsAssignableFrom(t)
select t;
//[Obsolete("Use Register(Component.For<I>().ImplementedBy<T>().Named(key).Lifestyle.Is(lifestyle)) instead.")]
//IWindsorContainer AddComponentLifeStyle<I, T>(string key, LifestyleType lifestyle) where T : class;
foreach (Type t in controllerTypes)
{
container.Register(Component.For<IController>().ImplementedBy<???>().Named(t.FullName).LifeStyle.Is(LifestyleType.Transient));
}
}
// Constructs the controller instance needed to service each request
protected override IController GetControllerInstance(Type controllerType)
{
return (IController)container.Resolve(controllerType);
}
}
Новое предложение - использовать Register (Component.For () .ImplementedBy
, но я не могу понять, как представить реализующий тип контроллера в методе ImplementedBy ??> ()
. Я пробовал ImplementedBy
и ImplementedBy
, но не могу найти подходящий способ передать тип реализации. Есть идеи?