一、描述问题

当托管代码调用非托管代码的时候,经常会出现如下报错:“尝试读取或写入受保护的内存。这通常指示其他内存已损坏”。

二、原因分析

由于非托管代码的内存指针的回收是由非托管代码自身手动完成的,而不是像托管代码一样有统一的垃圾回收机制,比如.NET的GC。

所以对于托管代码的调用方来说无法控制其内存回收。以上问题的产生原因很可能是托管代码调用了已经被回收的非托管对象。封装

的好一点的非托管代码一般都会有内存释放的接口供外部调用,这样调用方就可以管理非托管代码的内存回收。

三、解决方法

尽量不用使用不确定的非托管代码里面提供的对象。如果必须使用的话,实例化完成后直接使用而不要通过什么方法传递,委托回调等方式来

获取里面的对象,在这些复杂未知的过程中,很可能非托管的对象已经被回收了。

四、示例说明

当使用C#调用OpenCVSharp的时候,经常会出现以上问题。

错误代码如下:

1、订阅鼠标回调方法,并将mat的指针Data作为参数传递给回调方法。

   private void button15_Click(object sender, EventArgs e)
{
Mat mat = GetMat();//获取Mat对象
Cv2.SetMouseCallback("输入图像", GetRGBCvMouseCallback, mat.Data);
}

2、回调方法,获取每个点的RGB值

   private void GetRGBCallbackMethod(MouseEvent @event, int x, int y, MouseEvent flags, IntPtr userdata)
{
switch (@event)
{
case MouseEvent.LButtonDown: using (Mat mat = new Mat(Rows, Cols, _MatType, userdata))//这种方式会被内存回收,直接在这里面获取对象
{
for (int i = ; i < Rows; i++)
{
for (int j = ; j < Cols; j++)
{
Vec3b s = mat.At<Vec3b>(j, i);//获取第i0行第i1列) 这个方法会死 尝试读取收保护内存
} }
}
break;
default:
break;
}

运行报错,截图如下:

正确代码:

将7行代码Mat mat = new Mat(Rows, Cols, _MatType, userdata)改成using (Mat mat=GetMat()) ,就不会出现以上问题。

原因分析:

原因很可能是userData中回调的过程中已经被回收了,当再次使用时就会报尝试访问被保护的内存的错误。为了

防止此问题的发生,解决办法就是重新实例化一个Mat对象,不使用可能被回收的userData数据。

C# 调用OpenCVSharp报错“尝试读取或写入受保护的内存。这通常指示其他内存已损坏”的更多相关文章

  1. asp.net报错“尝试读取或写入受保护的内存。这通常指示其他内存已损坏”的解决办法

    来源:http://ajxfxb.blog.163.com/blog/static/56675086201411634336878/ 作者是:没完没了的工作 asp.net报错“尝试读取或写入受保护的 ...

  2. Sql Server尝试读取或写入受保护的内存。这通常指示其他内存已损坏

    今日遇到这样一个问题,用vs2010调试C#代码时,只要代码一运行到跟数据库关联的地方时,编译器就报错误,给的提示如:调试器已附加,要继续需要分离什么的,咋一看还以为是vs中调试器设置的问题,可后来仔 ...

  3. C#,调用dll产生 "尝试读取或写入受保护的内存 。这通常指示其他内存已损坏。"的问题

    由于易语言与c#做的DESC加解密方式,返回的数据不一致,所以,我用易语言写了一个dll,供c#调用, 结果在post的时候,有时候能正确返回数据,有时候则不能正常返回,而是返回空数据(c#没有做异常 ...

  4. SQLServer2012在登录远程服务器实例时报错:尝试读取或写入受保护的内存

    SQLServer2012在登录远程服务器实例时报错:尝试读取或写入受保护的内存.这通常指示其它内存已损坏.(System.Data). 而登录本地数据库实例则能顺利登入,不存在上述问题. 试一试重置 ...

  5. ArcEngine尝试读取或写入受保护的内存

    先说一下我的开发环境: Win10 + ArcGIS10.0 + ArcEngine10.0 + Framework4.0 今天调用新的GP工具则出现"尝试读取或写入受保护的内存.这通常指示 ...

  6. windows7 Sql server 2012 尝试读取或写入受保护的内存。这通常指示其他内存已损坏的修复

    项目中,使用了sql server2012数据库,服务端是2012,客户端如果是2008的话,就会报错: 索引错误. 没办法,就安装了sql server2012客户端.但是还是报错,无法连上数据库服 ...

  7. vs.net 2005 C# WinForm GroupBOX 的BUG?尝试读取或写入受保护的内存。这通常指示其他内存已损坏

    其实很久没有写程序了,国庆难得有空闲,写了个游戏辅助机器人,程序写好能用后本想把UI控件放到GroupBox里归下分类,美化下界面,结果一运行报“尝试读取或写入受保护的内存.这通常指示其他内存已损坏” ...

  8. System.AccessViolationException: 尝试读取或写入受保护的内存。这通常指示其他内存已损坏。

    系统debug时出现错误,System.AccessViolationException: 尝试读取或写入受保护的内存.这通常指示其他内存已损坏. Attempted to read or write ...

  9. C#尝试读取或写入受保护的内存。这通常指示其他内存已损坏。

    安装VS2013后,win7 + .net 4 + c#程序无法连接到SQL Server2000的实例 SQLServer2012在登录远程服务器实例时报错:尝试读取或写入受保护的内存. “尝试读取 ...

随机推荐

  1. .NET进阶篇06-async异步、thread多线程4

    知识需要不断积累.总结和沉淀,思考和写作是成长的催化剂 梯子 一.锁1.lock2.Interlocked3.Monitor4.SpinLock5.Mutex6.Semaphore7.Events1. ...

  2. 使用Jq实现弹出层

    对于前端程序员来说,弹出层是经常用到的,下面我叫大家如何用实现JQuery实现弹出层的效果,代码如下: CSS:弹出层的效果 .mask { position: absolute; top: 0px; ...

  3. 大型情感剧集Selenium:3_元素定位 #华为云·寻找黑马程序员#

    关于昨天的文章 今天有朋友反馈,代码运行的时候,selenium提示警告 DeprecationWarning: use options instead of chrome_options drive ...

  4. JS页面跳转和打开新窗口方式

    1.window.location.href=URL : 在本窗体打开一个新的页面,也是最常用的一种方法: 2.window.open(URL)  :  在一个新的窗口打开一个新的页面: 3.loca ...

  5. Spring boot 集成 阿里 Mqtt

    因为公司业务需求,需要接入 阿里Mqtt,自己基于Spring写了一个小demo,记录下来,已备以后需要. 第一步 创建一个实体bean用来装载 MqttClient private MqttClie ...

  6. wxxcx_learn独立验证与REST

    模块,控制器,方法 validate  接口参数校验 独立验证(验证器对独立验证做了更好的封装) $date = [ 'name' => '111', 'email' => '123@qq ...

  7. 2019年Dubbo你掌握的如何?快看看这30道高频面试题!

    前言 Dubbo是一个分布式服务框架,致力于提供高性能和透明化的RPC远程服务调用方案,以及SOA服务治理方案.简单的说,dubbo就是个服务框架,如果没有分布式的需求,其实是不需要用的,只有在分布式 ...

  8. gulp遇到错误:The following tasks did not complete: default Did you forget to signal async completion?

    运行之后会像下面一样报这个错误,因为事按着一个视频来写的,所以 原本的gulpfile.js如下 const gulp = require('gulp') gulp.task('default',() ...

  9. SSM项目整合纪实

    一 前 言 本来是为了探究一些功能性问题,需要一套完整的项目架构,本以为SSM用过那么多了,轻松搭建不在话下,但是过程中还是遇到一些问题,踩到一些未曾料想的坑.博文以搭建极简架构为目的,附带一些关键阐 ...

  10. 软件开发工具(第11章:Eclipse CDT开发常用功能)

    一.自定义编辑器 C/C++首选项设置(重点.记忆.应用) 单击菜单栏中的窗口(Window)菜单, 选择首选项(Preferences)选项,在 弹出的对话框左侧部分,展开C/C++树 形菜单. 外 ...