1

我有一个 Windows 服务,它会一直循环直到它停止。每个循环后有 15 秒的线程间隔。我正在使用统一容器来解析对象,如下所示:

var processes = ProcessConfigurationSection.GetProcesses();
while (!_stopped)
{
    try
    {
        foreach (var process in processes)
        {
            var worker = new Worker(DiContainer.UnityContainer.Resolve<IProcessDao>());
            worker.RunProcess(process.Name, process.StoredProcedure, process.BatchSize);
        }
        Thread.Sleep(_interval);
    }
    catch (Exception ex)
    {
        Log.LogEvent(...);
    }
}

我应该在while循环内创建一个worker的实例(并解析对象)还是应该在while循环之外以提高性能?此外,这两种方法都有内存泄漏的可能性吗?

4

1 回答 1

1

您通常应该定义一个“每个请求”的范围。对于 Web 应用程序,这通常是一个持续 Web 请求生命周期的范围。但是对于 Windows 服务应用程序,仍然存在请求,只有您必须决定您看到的请求是什么。每个RunProcess调用都可以是单个请求(因此是单个范围),或者处理整个批次processes可以视为单个请求。

您不应该在循环之外定义此范围,因为范围生活方式通常会实现诸如在整个请求中重用的工作单元实现之类的东西。例如实体框架DbContext是一个工作单元。您不希望DbContext在应用程序的整个生命周期内重复使用相同的内容,因为当操作失败时,您可能会破坏DbContext整个应用程序,从而破坏整个应用程序。

Unity 的作用域是使用子容器实现的。您应该使用以下内容包装您的请求:

using (var child =
    DiContainer.UnityContainer.CreateChildContainer())
{
    var worker = new Worker(child.Resolve<IProcessDao>());
    worker.RunProcess(process.Name, process.StoredProcedure,
        process.BatchSize);
}

或者也许using (var child应该包装foreach. 这是你必须决定的事情。

于 2013-03-05T15:26:33.737 回答