【问题标题】:Is Session variable thread-safe within a Parallel.For loop in ASP.Net pageASP.Net 页面中的 Parallel.For 循环中的 Session 变量是线程安全的吗
【发布时间】:2014-07-28 03:03:11
【问题描述】:

在下面的代码中更改会话变量(即 Session["Progress"])是否安全?

此代码是 ASP.Net 页面代码隐藏的一部分。

并行运行循环时,两个迭代可能同时运行,如果两个迭代都更改了同一个会话变量,则会导致问题。

   public void LongOperation()
    {
        Parallel.For(0, totalMembers,(i,loopState) =>
        {
            Thread.Sleep(2000);//wait some time to simulate processing
            progress++;
            Session["Progress"] = progress;//IS THIS THREAD-SAFE?
        } 
       ); 
   }

【问题讨论】:

  • 文档指出实例方法不是线程安全的。你为什么要做并行工作,你有没有想过它将如何消耗用于 asp.net 请求的线程? msdn.microsoft.com/en-us/library/…
  • 为了确保它是你总是可以实现一些锁定
  • @SimonSvensson,看看这个会话状态似乎是线程安全的:stackoverflow.com/questions/2715532/…
  • @SimonSvensson,在 ASP.Net 中是否不建议使用并行循环?我想,并行性会根据可用的 CPU、内存和线程自动优化自身,因此我可以毫无风险地使用它。
  • @Sunil,会话状态在“任何时候只有一个 http 请求写入会话”的上下文中是线程安全的。如果您启动自己的线程访问它,则没有线程安全性。并行的东西通常使用 ThreadPool 进行调度,与 asp.net 请求使用的线程相同,从而减少了可用于传入 http 请求的线程。你能告诉我们更多为什么你觉得需要并行的东西吗?你想解决什么问题?

标签: asp.net multithreading c#-4.0 task-parallel-library


【解决方案1】:

这不是线程安全的,但不同打开页面之间的会话可以安全更改

所以在某些情况下,如果你调用它是安全的。

如果您只从您的页面调用一次,那么跨不同页面是安全的。 原因是会话从页面加载开始到结束都完全锁定了会话。

一些类似的答案可以证明这一点。

Web app blocked while processing another web app on sharing same session
Does ASP.NET Web Forms prevent a double click submission?
Trying to make Web Method Asynchronous

如果您从同一页面不同的线程多次调用它,那么您需要同步

注意事项

  • 如果此循环需要很长时间才能完成,则 所有用户都将等待 该计算而不仅仅是会话用户。所有用户都将被会话锁锁定。如果太多用户调用,那么所有用户一起将等待很长时间。因此,您可能需要对调度程序任务进行此计算。
  • 如果处理循环内数据的时间小于循环创建和同步线程所用的时间,则并行循环需要更多时间完成比一个简单的循环。所以这里需要计算简单循环和并行循环的速度。

【讨论】:

    猜你喜欢
    • 2020-05-02
    • 2023-04-04
    • 2013-04-01
    • 1970-01-01
    • 2019-10-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多