继上次记一次w3wp占用CPU过高的解决过程(Dictionary和线程安全)后又再次与Dictionary博弈,这一次是在EntityFramework中的Dictionary。

从一个异常说起

这个异常与上次的异常有着同一个特性:间歇性,碰到类似的异常在信心上就被削弱了一大半。。。

在第一次看到这个异常的时候觉得解决它非常的简单,无非就是在字典操作的地方加个锁,但仔细看了一会发现这个问题并没有那么简单,可以看到这个异常的最后几个堆栈信息来自System.Data.Entity命名空间,也就是EntityFramework,这就使问题变得难以寻纠。

出错的地方就在FirstOrDefault,一个在简单不过的Linq方法。

反编译查看EntityFramework的实现

AddNewRelation方法的内容如下:

马上锁定了AddRelationshipEntryToDictionary,方法代码如下:

可以看出是EntityFramework添加状态监控相关的逻辑,看到这也大概猜出来了又是线程安全的问题,但为了确定我追纠了调用AddNewRelation的HandleRelationshipSpan方法。

代码比较复杂,较难看懂,于是就去EntityFramework源码托管的站上面去看看是否有写注释,碰碰运气。

果不其然还是存在比较详尽的注释

问题也大致清晰了,应该是线程共享的DbContext出现了问题。

用Demo还原异常

解决方案

因为我们并不想放弃线程内共享一个DbContext的方案,所以我们并没有从根本解决这个问题,我们把调用FirstOrDefault的操作放在了Lazy里面。

剩下的就是观察效果。

写在最后

写了两篇解决BUG的纪要不为了大家能快速解决问题,而为了交流一种寻找BUG解决BUG的思路与方法。

最后,福州地区有需要找工作或者想换工作的“猿”吗?如果有可以沟通沟通联系联系呗。

EntityFramework中的线程安全,又是Dictionary的更多相关文章

  1. 浅谈Excel开发:十 Excel 开发中与线程相关的若干问题

    采用VSTO或者Shared Add-in等技术开发Excel插件,其实是在与Excel提供的API在打交道,Excel本身的组件大多数都是COM组件,也就是说通过Excel PIA来与COM进行交互 ...

  2. C#中的线程(三) 使用多线程

    第三部分:使用多线程 1.  单元模式和Windows Forms 单元模式线程是一个自动线程安全机制, 非常贴近于COM——Microsoft的遗留下的组件对象模型.尽管.NET最大地放弃摆脱了遗留 ...

  3. Java5中的线程池实例讲解

    Java5增加了新的类库并发集java.util.concurrent,该类库为并发程序提供了丰富的API多线程编程在Java 5中更加容易,灵活.本文通过一个网络服务器模型,来实践Java5的多线程 ...

  4. C#中的线程(下)-多线程

    1.  单元模式和Windows Forms 单元模式线程是一个自动线程安全机制, 非常贴近于COM——Microsoft的遗留下的组件对象模型.尽管.NET最大地放弃摆脱了遗留下的模型,但很多时候它 ...

  5. 浅谈利用同步机制解决Java中的线程安全问题

    我们知道大多数程序都不会是单线程程序,单线程程序的功能非常有限,我们假设一下所有的程序都是单线程程序,那么会带来怎样的结果呢?假如淘宝是单线程程序,一直都只能一个一个用户去访问,你要在网上买东西还得等 ...

  6. Linux中epoll+线程池实现高并发

    服务器并发模型通常可分为单线程和多线程模型,这里的线程通常是指“I/O线程”,即负责I/O操作,协调分配任务的“管理线程”,而实际的请求和任务通常交由所谓“工作者线程”处理.通常多线程模型下,每个线程 ...

  7. “线程安全的” Dictionary(TKey,TValue)

    这是一篇翻译,专门介绍Dictionary线程安全问题,原文网址如下 http://www.grumpydev.com/2010/02/25/thread-safe-dictionarytkeytva ...

  8. C#中的线程(三)多线程

    C#中的线程(三)多线程   Keywords:C# 线程Source:http://www.albahari.com/threading/Author: Joe AlbahariTranslator ...

  9. c++11中的线程、锁和条件变量

    void func(int i, double d, const string& s) { cout << i << ", " << d ...

随机推荐

  1. which,whereis, locate, find

    which 在PATH环境变量中的路径中查找目标文件,所以用来查找都是可执行文件,Linux下的各种命令本质上就是一个可执行的文件,所以我们安装新的软件之后通常都会有相应的命令将其打开,就是因为安装的 ...

  2. mac svn 终端操作命令

    svn 删除目录命令 svn 提交命令 svn commit -m zenggui 出来要提交的目录后,按shift + : + q 如遇到不明白的可以输入:svn help 比如想查询删除命令的使用 ...

  3. nginx 平滑升级tengine

    wget  http://tengine.taobao.org/download/tengine-1.5.1.tar.gz //下载Tengine1.5.1版本 tar zxvf tengine-1. ...

  4. builder.properties

    请加上这句话: javacDefaultEncoding.. = UTF-8

  5. 我的NopCommerce之旅(6): 应用启动

    一.基础介绍 Global.asax 文件(也称为 ASP.NET 应用程序文件)是一个可选文件,该文件包含响应 ASP.NET 或 HTTP 模块所引发的应用程序级别和会话级别事件的代码. Appl ...

  6. uva 10129 play on words——yhx

    aaarticlea/png;base64,iVBORw0KGgoAAAANSUhEUgAABNUAAANeCAYAAAA1BjiHAAAgAElEQVR4nOydabWsuhaFywIasIAHJK

  7. TestNG之执行顺序

    如果很有个测试方法,并且这几个方法又有先后顺序,那么如果让TestNG按照自己想要的方法执行呢 一.通过Dependencies 1.在测试类中添加Dependencies @Test public ...

  8. [ZZ]最小化不可重现的bug

    http://testerhome.com/topics/577 原文请见 Minimizing Unreproducible Bugs 不能重现的 bug 是我的灾难.我常常找到一个bug 后来又听 ...

  9. POJ 3416 Crossing --离线+树状数组

    题意: 给一些平面上的点,然后给一些查询(x,y),即以(x,y)为原点建立坐标系,一个人拿走第I,III象限的点,另一个人拿II,IV象限的,点不会在任何一个查询的坐标轴上,问每次两人的点数差为多少 ...

  10. tomcat7 - 烫手山芋之热部署

    tomcat7部署,项目发布有很多种方式 1. 增量发布,把修改过得那些文件手动上传至tomcat,*.class *.xml 等等,这样的缺点非常大,需要断开tomcat,记住那些你修改过得文件,很 ...