【问题标题】:Caching data for lifetime of thread为线程的生命周期缓存数据
【发布时间】:2013-06-03 10:36:44
【问题描述】:

我正在寻找一种在线程的生命周期内缓存数据的方法。数据不需要跨线程访问。

ASP.NET 中,您可以使用HttpContext.Current.Items 集合来执行此操作。只要线程处于活动状态,您存储在此处的任何内容都会被保留,并且可以从任何类访问。

我想知道.NET 框架 (4.0) 中是否有更通用的等价物,它与HTTP.?? 无关

【问题讨论】:

    标签: .net multithreading c#-4.0


    【解决方案1】:

    使用默认值创建ThreadLocal<T> 对象后,您可以使用其 Value 属性来获取该值或将其设置为其他值。

    您可以创建任意数量的ThreadLocal<T> 对象,它们可以存储在实例或静态字段中。

    Thread.AllocateNamedDataSlot 确实在所有线程上分配了一个命名数据槽。但是,每个线程都有自己的这个命名槽的副本,因此它们不会相互干扰。

    线程本地存储的目的是为每个线程提供其自己的存储位置副本,而不是单独为一个线程创建存储。

    线程堆栈上的局部变量实现了后一个目标,只要线程的执行路径中只有一个方法调用,这就是你所需要的。

    但是,如果线程的执行路径中有多个方法调用,则必须在方法之间传递局部变量,这在实践中可能会很尴尬。这正是线程本地存储旨在解决的问题。

    【讨论】:

      【解决方案2】:

      您的问题的简单答案是在线程 proc 中创建缓存。例如:

      void MyThreadProc(object state)
      {
          var myCache = createDataCache();
          // myCache will available throughout the lifetime of the thread
      }
      

      正如您所指出的,如果您的线程包含在单个方法中,那就太好了。如果必须调用多个方法,则必须将该缓存传递给所有方法。

      另一种选择是让线程 proc 创建一个执行实际处理的类的实例,并让该类拥有缓存。所以你的线程过程看起来像:

      void MyThreadProc(object state)
      {
          var processor = new ThreadDataProcessor();
          processor.DoProcessing();
      }
      

      ThreadDataProcessor 构造函数将创建缓存,并在线程 proc 退出时释放所有缓存。如果ThreadDataProcessor 需要访问其他数据,则必须将对这些结构的引用传递给构造函数。

      线程本地存储可以工作,但是在混合使用线程本地存储和线程池时必须小心。池线程可以挂起很长时间(程序的生命周期),因此线程本地存储会累积。如果您有大量线程本地数据,这可能会占用大量内存。

      考虑到所有因素,如果在您的应用程序中这样做是合理的,我会推荐上面的第二种方法。

      【讨论】:

        猜你喜欢
        • 2012-08-27
        • 2022-06-12
        • 1970-01-01
        • 2016-09-08
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2011-04-11
        • 1970-01-01
        相关资源
        最近更新 更多