在线程之间锁定图像时出现问题

2023-11-29

我需要在两个不同的线程中获取锁,以便访问 EmguCv 中的位图(从网络摄像头填充)。 我有一个“GetFrame”函数,可以查询相机并将其返回的内容放入 .NET 位图中。我有两个线程需要访问此位图,一个需要写入位图并将位图分配给图片框,另一个需要读取位图,将其转换为图像对象并将其分配给 EMGU ImageBox。 我首先锁定任意对象,然后执行操作。代码如下(_Camera.LiveFrame为Bitmap):

写作/阅读主题:

while (_CaptureThreadRunning)
{
   lock (_Camera)
   { 
      // _Camera.GetFrame writes to the Bitmap
      if (_VideoPlaying && _Camera.GetFrame(500)) 
           pbLiveFeed.Invalidate();
    }
}
_Camera.CloseCamera(true);
_CaptureExitEvent.Set();           // Set to signal captureThread has finished

阅读/图像框主题:

while (_ProcessThreadRunning)
{
   lock (_Camera)
   {
      //  _Camera.LiveFrame is the Bitmap
      procImage = new Image<Bgr, int>((Bitmap)_Camera.LiveFrame.Clone());          
      procImage.Draw(new Rectangle(10,20,20,15),new Bgr(Color.LightGreen), 5);

      ibProcessed.Image = procImage;
      ibProcessed.Invalidate();
    }
}
_ProcessExitEvent.Set();

大多数情况下运行良好,但当我尝试 Clone() 位图时,我时不时会收到“对象在其他地方使用”错误。这不是正确的锁定方式吗?我不明白为什么这会引起问题。

附注我的线程也无法再正常退出。我的循环之外的 .Set() 调用永远不会被调用。我猜线程已经死锁了?


GDI+ 有一个锁定机制,可以防止两个线程使用位图对象——这就是您收到的错误。

当 UI 线程已经在访问位图时,您正尝试访问该位图。例如,1)您将位图分配给图片框,2)图片框失效然后重新绘制,3)您退出写/读线程锁,然后4)读/图像框线程尝试访问相同的重绘仍在发生时的位图。

要解决该问题,只需复制位图,然后使用该副本进行操作即可。无论您给图片框提供什么,都不要假设您可以从非 UI 线程再次触摸它。

例如,在 _Camera.GetFrame 中:

// Get the bitmap from the camera
capturedBitmap = GetFromCamera();

// Clone the bitmap first before assigning to the picture box
_Camera.LiveFrame = new Bitmap(capturedBitmap);

// Assign to the picture box
pbLiveFeed.Image = capturedBitmap;

现在,只要您有适当的锁定,就应该可以从线程访问 _Camera.LiveFrame。

我在这里要考虑的其他几个问题:

  1. 您提到您正在锁定一个“任意对象”,但 _Camera 似乎并非如此——它是一个可以以不可预测的方式在其他地方使用的对象。我建议制作一个仅用于锁定的对象,例如

    object lockObject = new lockObject;
    lock (lockObject)
    {
        // put your synchronized code here
    }
    
  2. Bitmap.Clone() 创建一个与原始位图共享像素数据的位图。当您转换为图像对象以分配给 EMGU ImageBox 时,您正在使用该克隆,它维护对位图的引用。因此,在我看来,创建一个新的位图比在这种情况下使用 Clone() 更安全。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

在线程之间锁定图像时出现问题 的相关文章

  • 无法使用 strptime() 获取秒数

    我收到 YYYY MM DDThh mm ss S Z hh mm 这种格式的日期时间 我正在尝试使用复制该值strptime如下所示 struct tm time 0 char pEnd strptime datetime Y m dT
  • UTF8/UTF16 和 Base64 在编码方面有什么区别

    In c 我们可以使用下面的类来进行编码 System Text Encoding UTF8 System Text Encoding UTF16 System Text Encoding ASCII 为什么没有System Text En
  • 在 LINQ 查询中返回不带时间的日期

    我正在编写一个查询 我想计算按日期联系我们的呼叫中心的次数 看起来很简单 但由于联系日期字段是日期时间字段 我得到了时间 因此当我按联系日期 时间 分组时 每个联系日期实例的计数为 1 所以 我想只按日期分组 而不按时间分组 下面是我用来查
  • 属性对象什么时候创建?

    由于属性实际上只是附加到程序集的元数据 这是否意味着属性对象仅根据请求创建 例如当您调用 GetCustomAttributes 时 或者它们是在创建对象时创建的 或者 前两个的组合 在由于 CLR 的属性扫描而创建对象时创建 从 CLR
  • 嵌入式系统中的malloc [重复]

    这个问题在这里已经有答案了 我正在使用嵌入式系统 该应用程序在 AT91SAMxxxx 和 cortex m3 lpc17xxx 上运行 我正在研究动态内存分配 因为它会极大地改变应用程序的外观 并给我更多的力量 我认为我唯一真正的路线是为
  • fgets() 和 Ctrl+D,三次才能结束?

    I don t understand why I need press Ctrl D for three times to send the EOF In addition if I press Enter then it only too
  • 为什么 POSIX 允许在只读模式下超出现有文件结尾 (fseek) 进行搜索

    为什么寻找文件结尾很有用 为什么 POSIX 让我们像示例中那样在以只读方式打开的文件中进行查找 c http en cppreference com w c io fseek http en cppreference com w c io
  • c# Asp.NET MVC 使用FileStreamResult下载excel文件

    我需要构建一个方法 它将接收模型 从中构建excel 构建和接收部分完成没有问题 然后使用内存流导出 让用户下载它 不将其保存在服务器上 我是 ASP NET 和 MVC 的新手 所以我找到了指南并将其构建为教程项目 public File
  • 当 Cortex-M3 出现硬故障时如何保留堆栈跟踪?

    使用以下设置 基于 Cortex M3 的 C gcc arm 交叉工具链 https launchpad net gcc arm embedded 使用 C 和 C FreeRtos 7 5 3 日食月神 Segger Jlink 与 J
  • .Net Core / 控制台应用程序 / 配置 / XML

    我第一次尝试使用新的 ConfigurationBuilder 和选项模式进入 Net Core 库 这里有很多很好的例子 https docs asp net en latest fundamentals configuration ht
  • Windows 窗体不会在调试模式下显示

    我最近升级到 VS 2012 我有一组在 VS 2010 中编码的 UI 测试 我试图在 VS 2012 中启动它们 我有一个 Windows 窗体 在开始时显示使用 AssemblyInitialize 属性运行测试 我使用此表单允许用户
  • 编译的表达式树会泄漏吗?

    根据我的理解 JIT 代码在程序运行时永远不会从内存中释放 这是否意味着重复调用 Compile 表达式树上会泄漏内存吗 这意味着仅在静态构造函数中编译表达式树或以其他方式缓存它们 这可能不那么简单 正确的 他们可能是GCed Lambda
  • 是否有比 lex/flex 更好(更现代)的工具来生成 C++ 分词器?

    我最近将源文件解析添加到现有工具中 该工具从复杂的命令行参数生成输出文件 命令行参数变得如此复杂 以至于我们开始允许它们作为一个文件提供 该文件被解析为一个非常大的命令行 但语法仍然很尴尬 因此我添加了使用更合理的语法解析源文件的功能 我使
  • 我的 strlcpy 版本

    海湾合作委员会 4 4 4 c89 我的程序做了很多字符串处理 我不想使用 strncpy 因为它不会终止 我不能使用 strlcpy 因为它不可移植 只是几个问题 我怎样才能让我的函数正常运行 以确保它完全安全稳定 单元测试 这对于生产来
  • 网络参考共享类

    我用 Java 编写了一些 SOAP Web 服务 在 JBoss 5 1 上运行 其中两个共享一个类 AddressTO Web 服务在我的 ApplycationServer 上正确部署 一切都很顺利 直到我尝试在我的 C 客户端中使用
  • 将应用程序从 Microsoft Access 迁移到 VB 或 C#.NET

    我目前正试图说服管理层需要将我们的应用程序之一移植到 NET 该应用程序已经发展成为 Access 中的一个庞然大物 SQL 后端 拥有 700 个链接表 650 个表单 子表单 130 个模块和 850 个查询 我几乎知道这样做的所有主要
  • EPPlus Excel 更改单元格颜色

    我正在尝试将给定单元格的颜色设置为另一个单元格的颜色 该单元格已在模板中着色 但worksheet Cells row col Style Fill BackgroundColor似乎没有get财产 是否可以做到这一点 或者我是否必须在互联
  • 如何在内存中存储分子?

    我想将分子存储在内存中 这些可以是简单的分子 Methane CH4 C H bond length 108 7 pm H H angle 109 degrees But also more complex molecules like p
  • Bing 地图运行时错误 Windows 8.1

    当我运行带有 Bing Map 集成的 Windows 8 1 应用程序时 出现以下错误 Windows UI Xaml Markup XamlParseException 类型的异常 发生在 DistanceApp exe 中 但未在用户
  • 如何使用 ReactiveList 以便在添加新项目时更新 UI

    我正在创建一个带有列表的 Xamarin Forms 应用程序 itemSource 是一个reactiveList 但是 向列表添加新项目不会更新 UI 这样做的正确方法是什么 列表定义 listView new ListView var

随机推荐

  • 如何将新数组插入到我的锯齿状数组中

    你好 我将非常感谢任何帮助 好吧 让我们看看 首先我声明了一个像这样的锯齿状数组和下一个代码 int n 1 m 3 p 0 int jag array new n 现在我的锯齿状数组内部将有 1 个数组 接下来必须像这样填充数组 car
  • 如何在没有显式嵌套循环的情况下生成 N 个元素的组合,每个元素的供应有限

    如果 N 是固定的 比如 N 3 那么很容易 我可以使用深度为 3 的嵌套循环 例如 from i in Enumerable Range 0 2 from j in Enumerable Range 0 2 from k in Enume
  • CodeIgniter - 检查真实结果的最佳方法

    检查模型或其他任何地方的某些方法是否正确执行的最佳方法是什么 这是个好办法吗 Model data field1 this gt input gt post field1 data field2 this gt input gt post
  • BASH 脚本根据日期复制文件,但有一个问题

    让我解释一下树结构 我有一个网络目录 我们的数据库每天会多次复制新的 txt 文件 这些文件位于基于用户名的目录中 在本地磁盘上 我具有相同的结构 基于用户名的目录 并且需要使用最新的 txt 文件进行更新 这不是同步过程 我将远程文件复制
  • 列出 C# 中的 GetRange 错误

    我正在处理列表 我的列表有 14 条记录 List
  • 用于.Net项目的文档数据库/键值存储[关闭]

    就目前情况而言 这个问题不太适合我们的问答形式 我们希望答案得到事实 参考资料或专业知识的支持 但这个问题可能会引发辩论 争论 民意调查或扩展讨论 如果您觉得这个问题可以改进并可能重新开放 访问帮助中心以获得指导 是否有与 Net 项目配合
  • 变量赋值避免无限循环

    我有两段递归代码 打算递归地打印出数组的一半 直到到达数组长度为 1 的数组 没有变量赋值的代码无限运行 而有变量赋值的代码则按预期运行 有任何线索说明为什么会出现这种情况吗 无限运行 CAREFUL function half arr h
  • 突出显示 DBGrid 中的特定文本

    我正在执行查询并在 dbgrid 中显示返回的数据 我想突出显示符合搜索条件的项目 就像是 搜索方式 test 在 DBGrid 中 返回的数据将为 ID Return 1 This is a test 2 Test ing 这里的目标无疑
  • 如何确定 SharePoint 列表的磁盘大小?

    我有一个包含大约 5500 个项目的列表 我想了解磁盘上的大小 我有什么办法可以做到这一点吗 如有必要 我不介意在数据库中运行查询 导航http myapplication mySitecollection layouts storman
  • 类型 将指数数转换为 int 或 float

    下面的代码 echo int 2e2 echo int 2e2 echo float 2e2 outputs 2 200 200 我不知道为什么 谢谢 2e2 is scientific notation meaning 2 102 200
  • 使用 invalidateOptionsMenu() 打开/关闭 NavDrawer 会导致 SearchView 上的 onRestore 调用和 onQueryTextChange 也被调用

    我有一个带有回调实现的 MainActivity DrawerListFragment Callback ItemListFragment Callbacks SearchView OnQueryTextListener 我还添加了一个 A
  • 我对drawable-hdpi 和drawable-mdpi 感到困惑

    我正在尝试让我的 Android 应用程序在手机类型设备和平板电脑上运行 对于布局 我有layout normal和layout large 并且我将xml文件放入每个布局中 似乎为每个设备选择了正确的布局 手机的layout normal
  • 芹菜组和链

    我需要对 Celery 中的一些任务进行排序 其中一些应该作为单个任务 一些应该并行工作 当组中的任务完成时 它应该传递下一个任务 chain task1 s task2 s group task3 s task4 s group task
  • 在C中反转单​​链表[重复]

    这个问题在这里已经有答案了 可能的重复 如何仅使用两个指针反转单链表 这是反转链表的 C 代码 但这并没有产生所需的输出 struct node temp prev while head gt next NULL temp prev hea
  • 混合模式 C++/CLI 应用程序未正确关闭 CLR

    我的混合模式 MFC 应用程序正在创建错误的内存泄漏 因为 CRT 没有时间在 MFC dll 关闭之前关闭 我有一个非常简单的小应用程序来显示问题 include
  • 具有本地化内容的 ASP.NET 密码恢复控件

    我正在使用 ASP NET 成员资格和登录控件开发一个简单的门户应用程序 我想使用 PasswordRecovery 控件发送包含忘记密码的电子邮件 但我的门户需要本地化 我有一个现有的内容管理系统 我正在从中提取本地化字符串 并且我想将
  • MySQL:ORDER BY RAND() 的替代方法

    我读过一些 MySQL 的替代品ORDER BY RAND 函数 但大多数替代方案仅适用于需要单个随机结果的情况 有谁知道如何优化返回多个随机结果的查询 例如 SELECT u id p photo FROM users u profile
  • Android 连接 2 个音频(wav 或 mp3)文件

    我必须连接 2 个或更多音频 wav 或 mp3 文件并获取一个音频文件 我怎样才能在安卓中做到这一点 提前致谢 下面的代码部分将按照已进行的选择数量进行工作 选择意味着选择了多少个文件 将两个 wav 文件放入 sdcard0 SSoft
  • 将 list_selector_background 用作 LayerList 可绘制的 ListView 项目

    如果我们使用 ListView 或 ExpandableListView 默认背景是 android drawable list selector background 我有一个 ExpandableListView 它显示按日期分组的数据
  • 在线程之间锁定图像时出现问题

    我需要在两个不同的线程中获取锁 以便访问 EmguCv 中的位图 从网络摄像头填充 我有一个 GetFrame 函数 可以查询相机并将其返回的内容放入 NET 位图中 我有两个线程需要访问此位图 一个需要写入位图并将位图分配给图片框 另一个