如何解决DotNET中跨线程访问控件的问题

.NET后端中的跨线程控件操作 在线程安全性异常中,常见的异常是“在不是创建控件的线程上访问控件”(“Cross-thread operation not valid: Control accessed from a thread other than the thread it was created on.”)。当我们在一个线程中访问或修改UI控件时,如果这个控件是在另一个线程中创建的,就会引发线程安全性异常。方法中,我们首先检查是否需要跨线程访问控件,如果需要,我们使用委托调用将方法推迟到创建控件的线程上。然后,我们定义了一个。 阅读详情

如何解决DotNET中跨线程访问控件的问题

                     朱二(2008.10,转载请保留作者)                 

 

如果您对这篇小文感兴趣的话,或许您在编程中时候碰到过以下类似的异常提示:
1、线程间操作无效: 从不是创建控件“X”的线程访问它。(X是控件名称)
2、"在该控件上执行的操作正从错误的线程调用。使用 Control.Invoke 或 Control.BeginInvoke 封送到正确的线程才能执行此操

作。"

看到这种提示,极有可能是跨线程访问控件造成的。举个小例子,窗体FormA上有一位名叫TextBoxA的TextBox大哥。
代码如下:

  1.     Private Sub FormA_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
  2.         Dim th As New System.Threading.Thread(AddressOf CrossThreadCallTest)
  3.         th.Start()
  4.     End Sub
  5.     Public Sub CrossThreadCallTest()
  6.         TextBoxA.Text = "ABC"
  7.     End Sub

简单解释一下:
窗体加载时创建线程th执行过程CrossThreadCallTest,在线程th里面设置TextBoxA的文本。
TextBoxA是主线程创建的,在th线程里访问,造成跨线程访问Windows控件,通常您会得到类似上面的第一个提示。
错误消息如下:
在该控件上执行的操作正从错误的线程调用。使用 Control.Invoke 或 Control.BeginInvoke 封送到正确的线程才能执行此操作。

这样的问题在使用Visual Studio 2003的时候是遭遇不到的,在.NET Framework 2.0中,要想和避免同样的问题,可以采用一个简

单的方法,只要将TextBox类的CheckForIllegalCrossThreadCalls属性设置为False就可以,新代码如下

  1.     Private Sub FormA_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
  2.  TextBox.CheckForIllegalCrossThreadCalls = False
  3.         Dim th As New System.Threading.Thread(AddressOf CrossThreadCallTest)
  4.         th.Start()
  5.     End Sub

但CheckForIllegalCrossThreadCalls并不能解决所有的问题,比如TreeView控件就没有这么幸运,通常会抛出上面第2种提示。并且

对于跨线程访问Windows控件,微软似乎并不推荐使用CheckForIllegalCrossThreadCalls,而推荐采用更为安全的访问技术。
下面这个例子是跨线程向TreeView添加节点的例子:

  1.    Private Sub FormA_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
  2.         Dim th As New System.Threading.Thread(AddressOf CrossThreadCallTest)
  3.         th.Start()
  4.     End Sub
  5.     Public Sub CrossThreadCallTest()
  6.         Dim delAdd As New AddNodeDelegate(AddressOf AddTreeNode)
  7.         TreeView1.BeginInvoke(delAdd)
  8.     End Sub
  9.     Private Delegate Sub AddNodeDelegate()
  10.     Private Sub AddTreeNode()
  11.         TreeView1.Nodes.Add("ABC")
  12.     End Sub

这样一来,AddTreeNode过程还是在主线程里运行,当然不会出现跨线程的问题了,对代码稍加改动,就能说明:

  1.    Private Sub FormA_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
  2.         System.Threading.Thread.CurrentThread.Name = "Main"
  3.         Dim th As New System.Threading.Thread(AddressOf CrossThreadCallTest)
  4.         th.Name = "th"
  5.         th.Start()
  6.     End Sub
  7.     Public Sub CrossThreadCallTest()
  8.         Dim delAdd As New AddNodeDelegate(AddressOf AddTreeNode)
  9.         TreeView1.BeginInvoke(delAdd)
  10.     End Sub
  11.     Private Delegate Sub AddNodeDelegate()
  12.     Private Sub AddTreeNode()
  13.         TreeView1.Nodes.Add("ABC")
  14.         '显示的应该是Main
  15.         MessageBox.Show(System.Threading.Thread.CurrentThread.Name)
  16.     End Sub

 

就写这么多,欢迎以评论的形式讨论。

5-->详解《switch 数据接收驱动框架、mtk7621集成交换芯片mt7530》之一 SWITCH 交换芯片驱动配置: 一、 配置 MDIO 总线 二、配置 MAC 接口 三、基于 MAC 的 DMA 配置 四、设备驱动结构体 五、数据收发包 阅读详情

相关推荐

别再为UE5像素流部署踩坑了!Windows服务器单实例保姆级避坑指南(含Node.js证书、coturn空文件夹等常见问题解决)

本文提供了UE5像素流在Windows服务器单实例部署中的全面解决方案,涵盖Node.js证书过期、coturn空文件夹等常见问题。通过详细的步骤指导和配置建议,帮助开发者高效完成部署,避免常见陷阱,特别适合局域网环境下的应用场景。

weixin_30315435的博客 464

简述.Net Framework和.Net Core使用EntityFramework中DBContext多线程所引发问题的解决方案

以下描述,仅代表个人看法,如果有不同看法欢迎讨论 在开发过程中EF是一个使用率较高ORM框架,但是对于新人来说需要知道的一点就是EF中的数据上下文(DBContext)是非线程安全的。 在单元模式设计的框架中 ...

m0_37554403的博客 2877

AMCL代码详解(六)amcl中的重采样

每次都从w1左边的竖线开始转,显而易见,转到w1的概率为0-w1之间的随机数,转到w2的概率为w1到w1+w2之间的随机数,转到w3的概率为w1+w2到w1+w2+w3之间的随机数,后面的依次类推。当某个粒子的权值较大的时候,产生的随机数落在相应区间的概率就会增大,从而实现了对权值大粒子的多次复制,权值小的粒子的剔除。可以看出,在整个重采样的过程中,粒子进行了两次种情况的刷新,一种是随机生成的新的粒子,一种是对原来的粒子的复制。得到的值越大,说明粒子的权重越小,当前粒子的可信度比较小,需要重采样粒子。

YiYeZhiNian的博客 1579

dotnet多线程

一、线程池 用Thread创建线程时,一定是新线程。如果一直创建新线程来实现逻辑,创建线程将是性能的瓶颈。针对线程的复用就有了线程池的概念,线程池中会始终维持一定数量的线程,当需要新的线程使用时,线程池会分配出空闲的线程,而不需要额外创建。当线程结束后,线程池会回收并等待下次分配。 使用线程池的线程一般使用Task类实现。 最小线程池个数是CPU的核心数,最大线程池个数是32767。dotnet 生成新线程的规则是,当有新任务需要线程时,先在线程池中找空闲线程,如果没有空闲,就等待500ms看是否有线

weightking的博客 759

ESP32-P4开发板实战:从零配置VSCode环境到点亮MIPI-DSI屏幕(避坑指南)

本文详细介绍了ESP32-P4开发板在VSCode环境下的配置流程,包括SDK安装、idf_component.yml依赖管理,以及MIPI-DSI屏幕驱动的实现方法。通过实战指南帮助开发者避开常见配置陷阱,快速完成从环境搭建到屏幕点亮的全流程,适用于物联网和嵌入式开发场景。

pp12345的博客 742

Avalonia 超级详细学习指南

什么是 Avalonia?Avalonia 是一个开源的、跨平台的 GUI 框架,允许开发者使用 XAML 和 C# 构建现代化、高性能的桌面应用程序。与其他框架相比,Avalonia 具有强大的跨平台能力和灵活的界面设计。} }()Avalonia 的特点和优势跨平台性:Avalonia 可以在 Windows、Linux、macOS 等多个平台上运行,开发者可以编写一套代码,然后在不同的操作系统上运行相同的应用程序。

仰望星空的博客 1万+

在该控件上执行的操作正从错误的线程调用。使用 Control.Invoke 或 Control.BeginInvoke 封送到正确的线程才能执行此操作。

环境: C#   VS2010  .NET 4.0 错误原因: 在多线程中,窗体控件的元素不是线程安全的。除了UI线程,其他线程不可以对控件进行操作; 解决办法: (1) 可以通过异步委托调用来调用控件的方法来实现 注意:一般的委托是以同步方式来实现的 BeginInvoke(); 返回类型:IAsyncResult EndInvoke(); 传入IAsyncResult,返回

白永辉的专栏 3392

2023华为od机试真题【恢复数字序列】C++

2023华为od机试真题【恢复数字序列】C++ 对于一个连续正整数组成的序列,可以将其拼接成一个字符串,再将字符串里的部分字符打乱顺序。如序列8 9 10 11 12,拼接成的字符串为89101112,打乱一部分字符后得到90811211,原来的正整数10就被拆成了0和1。现给定一个按如上规则得到的打乱字符的字符串,请将其还原成连续正整数序列,并输出序列中最小的数字. 输入描述

MISAYAONE的博客 5729

在该控件上执行的操作正从错误的线程调用。使用 Control.Invoke 或 Control.BeginInvoke 封送到正确的线程才能执行此操作。(以解决)

如果您对这篇小文感兴趣的话,或许您在编程中时候碰到过以下类似的异常提示:1、线程间操作无效: 从不是创建控件“X”的线程访问它。(X是控件名称)2、"在该控件上执行的操作正从错误的线程调用。使用 Control.Invoke 或 Control.BeginInvoke 封送到正确的线程才能执行此操作。"看到这种提示,极有可能是跨线程访问控件造成的。举个小例子,代码如下: using System;

zjx19881002的专栏 2761

【Python机器学习】主成分分析(PCA):高维数据的“瘦身术“

主成分分析(PCA)的历史可以追溯到1901年,当时Karl Pearson首次提出了这个概念。在计算机还不存在的年代,PCA是一个纯粹的数学构想,用来简化多变量数据的分析。几十年后,当计算机出现时,PCA成为了数据分析中最早实现的算法之一。从那时起,超过一个世纪的发展中,PCA一直保持着其核心的理论框架和实用价值,这本身就是对这个方法深刻科学性的证明。在现代深度学习时代,许多人可能会认为PCA已经过时了。但事实恰好相反。

nmdbbzcl的博客 981

【基于CKF的IMM】CV和CT两个模型下的IMM,二维,滤波使用CKF(容积卡尔曼滤波),附完整的matlab代码

该文章摘要: 本文提出了一种基于交互多模型(IMM)和容积卡尔曼滤波(CKF)的融合定位算法,用于解决目标在直线运动和转弯机动之间的模型切换问题。通过MATLAB仿真实现了IMM-CKF算法,并与单一的CV-CKF(匀速模型)和CT-CKF(匀角速转弯模型)方法进行对比。实验结果表明,在包含直线段和转弯段的复合轨迹跟踪中,IMM-CKF方法能够自适应调整模型权重,显著提高了定位精度。轨迹跟踪图、位置/速度误差对比图以及模型概率曲线直观展示了IMM算法的优势。文章提供了完整的MATLAB实现代码,可用于目标跟

985工科博士毕业,专攻定位、导航和滤波等算法研究。从业10年,主要使用MATLAB 615

C#中跨线程访问控件

net 原则上禁止跨线程访问控件,因为这样可能造成错误的发生,推荐的解决方法是采用代理,用代理方法来间接操作不是同一线程创建的控件。第二种方法是禁止编译器对跨线程访问作检查,可以实现访问,但是出不出错不敢保证Control.CheckForIllegalCrossThreadCalls = false; 最近我在做一个项目,遇到了跨线程要去访问页面控件.但是总是提示出错,不能在其它线...

diaoquan8892的博客 239

大语言模型在金融风险预警中的推理应用探索

金融行业一直面临着各种风险,如信用风险、市场风险、操作风险等。准确及时的风险预警对于金融机构的稳定运营和投资者的利益保护至关重要。传统的金融风险预警方法主要基于结构化数据和统计模型,虽然在一定程度上能够识别风险,但对于非结构化数据的处理能力有限,难以捕捉到复杂的风险因素和潜在的风险趋势。大语言模型作为自然语言处理领域的重要突破,具有强大的语言理解和生成能力,能够处理各种形式的文本数据。

AI天才研究院 1169

使用invoke方法解决跨线程访问的问题

C#中禁止跨线程直接访问控件,InvokeRequired是为了解决这个问题而产生的,当一个控件的InvokeRequired属性值为真时,说明有一个创建它以外的线程想访问它。 获取一个值,该值指示调用方在对控件进行方法调用时是否必须调用 Invoke 方法,因为调用方位于创建控件所在的线程以外的线程中。 如果从另一个线程调用控件的方法,那么必须使用控件的一个 Invoke 方法来将调用封送到适当...

欢迎私信、留言交流 2452

温度PID控制PLC程序

温度PID稳定控制程序,适用于欧姆龙PLC,对其他PLC也具有很大参考价值

怀旧版电脑GBC模拟器

再现原版GBC掌机的界面,电脑运行连游戏界面都一样大小,很怀旧,很真实,(英文版)强烈推荐,很小的文件,很难才找到的。

跨线程访问webBrowser控件

private void button2_Click(object sender, EventArgs e)         {  th = new Thread(huoqu);                 th.IsBackground = true;                 th.Start();                  }        public

Bychentufeiyang的专栏 4425

文档:亲测可用解决vnc灰屏,黑屏,鼠标大黑叉情况

主要解决vnc-viewer灰屏,黑屏,鼠标大黑叉等现象,详细见文档。

c#使用MethodInvoker解决跨线程访问控件

c#使用MethodInvoker解决跨线程访问控件 .net 原则上禁止跨线程访问控件,因为这样可能造成错误的发生,有一种方法是禁止编译器对跨线程访问作检查,Control.CheckForIllegalCrossThreadCalls = false;可以实现访问,但是出不出错不敢保证C#跨线程访问控件运行时错误。 使用MethodInvoker即可解决: 原代码:

u011555996的博客 886

VC中sqlite的使用

在VC中对sqlite的使用,实现数据库大批数据的快速插入,读取数据库中的数据在ListCtrl中显示

使用MethodInvoker委托进行跨线程访问

使用MethodInvoker委托进行跨线程访问  (2007-03-30 09:45:37) 转载▼ 标签:  科学   MethodInvoker 提供一个简单委托,该委托用于调用含 void 参数列表的方法。在对控件的 Invoke 方法进行调用时或需要一个简单委托又不想自己定义时可以使用该委托(摘自MSDN)   在多

菜逼成长录 2380

多线程访问服务器控件出错

线程间操作无效: 从不是创建控件“richTextBox1”的线程访问它。 这个错误需要一个委托来解决private delegate void SetRichText(string txt,bool b); private void SetText(string txt,bool b) { if (richTextBox1.InvokeR

Json1204的专栏 726

[转] c#中 多线程访问winform控件

原文 c#中多线程访问winform控件的若干问题小结 我们在做winform应用的时候,大部分情况下都会碰到使用多线程控制界面上控件信息的问题。然而我们并不能用传统方法来解决这个问题,下面我将详细的介绍。 传统方法: public partial class Form1 : Form { public Form1() { ...

weixin_30279315的博客 86

C# 跨线程赋值的简单做法

通常,C#是不许跨线程赋值的,如:Form1中有个textbox, 若开辟一个新的线程来给 这个textbox赋值时,会出现异常。 MSDN中提出了具体的做法,较为繁琐,就不说了。 我这里有个简单办法。 大多数能赋值的控件都有invoke 方法,invode方法中不是要一个Delegate型参数么, 那简单,可以随便找个.NET自定义的Dele...

weixin_30889885的博客 582

DotNet中异步编程的简单应用

这里说的异步编程并不是AJAX等的Web异步编程,而仅仅是DotNet中多线程的异步编程.这种多线程的异步编程主要用来解决某些受计算操作影响而引起主线程阻塞的问题.让程序(主要是窗体应用程序)看跑得更流畅.在dotnet的CLR以及API方法中有简单易用的方法供我们实现异步编程,并且都有相似的调用方法,诸如BeginXXX,EndXXX,IAsyncResult对象,同时也都涉及到回调,委托等操作...

gtts 213

MethodInvoker 委托

MethodInvoker 提供一个简单委托,该委托用于调用含 void 参数列表的方法。在对控件的 Invoke 方法进行调用时或需要一个简单委托又不想自己定义时可以使用该委托(摘自MSDN)   在多线程编程时,DotNet2.0会对跨线程访问控件进行限制的,说是为了线程安全。   MSDN提供一种声明委托的例子,使用MethodInvoker可以不用声明的 如: private

qq408146580的专栏 3282

paip.c#.net 多线程调用控件的问题

paip.c#.net 多线程调用控件的问题 作者Attilax ,  EMAIL:1466519819@qq.com 直接调用会提示跨线程错误..使用委托也可以,但是代码分散了。使用以下方法更好,增强可读性。。 需要使用以下方法调用(实质上也是委托,但是应该是语法糖了,很好用)             label9.Invoke(new EventHandle

attilax的专栏 2321

【转】C#窗体中Invoke和BeginInvoke方法详解(一)

在Invoke或者BeginInvoke的使用中无一例外地使用了委托Delegate。   一、为什么Control类提供了Invoke和BeginInvoke机制? 关于这个问题的最主要的原因已经是dotnet程序员众所周知的,我在此费点笔墨再次记录到自己的日志,以便日后提醒一下自己。 1、windows程序消息机制 Windows GUI程序是基于消息机制的,有个主线程维护着一个消

doumin的专栏 1640

【转载】C# 使用多线程访问wi…

C# 使用多线程访问winform中控件 我们在做winform应用的时候,大部分情况下都会碰到使用多线程控制界面上控件信息的问题。然而我们并不能用传统方法来做这个问题,下面我将详细的介绍。 传统方法: 使用多线程访问winform中控件" /> 1 public partial class Form1 : Form 2 { 3 public Form1() 4

张志鹏的博客 296
上一篇: Remoting在Internet环境下的测试
下一篇: 中国不需要平准基金
「已注销」
博客等级 码龄25年 93粉丝 101原创
评论 3
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值