7

我的应用程序中有一个要求,我认为可以通过使用线程本地存储来满足,但我想知道这是否是最好避免的事情之一。

我已经阅读了一些关于这个主题的文章:

http://www.dotnetcoders.com/web/Articles/ShowArticle.aspx?article=58

http://msdn.microsoft.com/en-us/library/system.threadstaticattribute(vs.80).aspx

我知道如何使用它,我只是想知道我是否应该使用它。

有什么建议,需要注意的地方吗?

[编辑]

这是用例:

我通过一些方法汇集所有数据访问,这些方法对每个查询进行大量记录。我记录的一件事是命令文本的完整转储,其中填充了命令,以便我可以简单地从跟踪日志中直接复制粘贴到 Sql Management Studio 中。

在我的网络应用程序的 global.asax 中,当我遇到未处理的异常时,我会向管理员发送尽可能多的信息的电子邮件。当我收到 SqlException 时,我想将该 sql 命令转储文本放入这封电子邮件中,这将节省我在页面因查询而崩溃时挖掘跟踪日志的时间。

我不想更改我的数据访问类的方法签名,这样我就可以一直向下传递一些引用,只是为了在遇到异常时将其取出。我在想也许 TLS 是放置“lastsqlcommand”之类的好地方,但这看起来不是一个可行的解决方案。

4

3 回答 3

7

asp.net 应用程序的一个陷阱:单个请求的处理可能会切换线程,即如果同一会话中有并行请求。因此,您在 HttpApplication.PostRequireRequestState 事件之前放入 TLS 的任何内容都可能稍后不会出现,因为您在不同的线程上。

[提问者编辑]

对于我的特定用例,我最终将键值对添加到 SqlException.Data 字典中,然后在记录异常详细信息时检索它。这给了我希望使用线程本地存储的功能。

于 2008-10-06T16:53:41.417 回答
6

线程本地存储是修复在线程之前设计并使用大量全局变量和静态的库的一种快速方法。这是 C 标准库在不更改其接口的同时保持线程安全的方式(在内部,许多函数使用静态缓冲区)。

一般来说,这对这个目的是有好处的。如果您必须在多线程环境中拥有全局数据,那么线程本地存储是一个不错的选择。一个常见的原因是您正在调用一个第三方函数,该函数在同一个堆栈帧中回调您,但没有为您提供传递额外信息的钩子——当您尝试将较旧的 C 库包装在。网。

于 2008-10-06T17:26:28.010 回答
0

通过示例查看新的 .net 4 ThreadLocal<T>类,这里有更多信息。

于 2012-02-29T10:32:41.933 回答