1

我正在处理 ASP.NET 项目,昨天我看到一段代码使用 System.Threading.Thread 将一些任务卸载到新线程。该线程运行一些 SQL 语句并记录结果。

使用另一种方法不是更好吗?例如,拥有一个执行 SQL 批处理的 Windows 服务。然后网页将仅将批处理排入队列(通过 WCF)。

一般来说,ASP.NET 中多线程的最佳实践是什么?线程/TPL 任务/等的使用是否合理?在网页中?

4

2 回答 2

2

我在 ASP.NET 中使用多线程时的想法:

  1. ASP.NET 出于某些原因(例如您更改 web.config 或在一段时间内避免内存泄漏)回收 AppDomain。问题是你不知道回收的确切时间。长时间运行的线程不适合,因为当 ASP.NET 回收时,它会相应地降低您的线程。这种情况的正确方法是长时间运行的任务应该通过队列在后台进程上运行,就像你提到的那样。

  2. 对于短期运行和触发并忘记任务TPLasync/await是最合适的,因为它不会阻塞线程池中的线程以用于 HTTP 请求。

于 2012-11-02T06:29:20.787 回答
0

在我看来,这应该通过在数据库中提高某种标志和定期检查标志并启动作业的 Windows 服务来解决。如果作业过于频繁,则应使用专用队列解决方案(MSMQ、RabbitMQ 等)以避免数据库过载或表增长过快。我不认为通过 WCF 或其他任何方式直接与 Windows 服务通信是一个好主意,因为这可能会导致消息丢失。

话虽如此,有时项目需要在共享主机中运行,并且无法设置专用的 Windows 服务。在这种情况下,可以接受一个线程作为解决方法,一旦项目增长到足以拥有自己的服务器,就应该将其删除。

我相信 ASP.NET 中的所有其他线程都是一个问题的迹象,除了使用任务来表示异步操作,或者在极少数情况下,当您想在 Web 项目中并行执行计算但您的项目只有很少的并发用户(并发用户数少于核心数)

为什么任务在 ASP.NET 中很有用?

使用 Tasks 进行异步操作的第一个原因是,从 .NET 4.5 开始,异步 API 返回 Tasks :) 异步操作(不要与并行计算混淆)可能是 Web 服务调用、数据库调用等。它们可能对两件事有用:

  1. 一次解雇几个,你的工作将花费相当于最长操作的时间。如果您以顺序(非异步)方式触发它们,它们将花费等于每个操作时间总和的时间,这显然更多。
  2. 他们可以通过释放执行页面的线程来提高可伸缩性 - Node.js 样式。ASP.NET 一直支持这一点,但在 4.5 版中它真的很容易使用。我会声称它比 Node.js 更容易,因为 async/await。释放线程很重要,因为您可能会通过让它们等待来耗尽池中的线程。结果是当有一定数量的用户时,您的网站会变得很慢,尽管 CPU 使用率大约是 30%,这仅仅是因为新请求在队列中等待。如果您增加线程池中的线程数,那么您付出的代价就是持续的上下文切换,而不是操作系统。在某些时候,您将获得 100% 的 CPU 使用率,但其中 40% 将用于上下文切换。您将增加吞吐量,但收益递减。
于 2012-11-01T20:39:32.507 回答