多线程异常问题请教

_少年已不年_少 2015-01-05 12:09:37
最近写一个程序,是WINform的,功能是这样的,通过主窗体按钮调用读卡器的动态链接库联网去读取卡片信息,就跟读取银行卡信息一样。但是由于网络,或者对方服务原因,当我点击读卡按钮到获取卡片信息呈现到窗体控件上,差不多会有1秒到2秒的主窗体卡顿情况.因此就想使用多线程来解决,保证主窗体不卡顿。但是有这么一种情况,在读卡的过程中,对方返回信息后会有一个成功的返回标志0,但是在读卡过程中可能会有各种原因导致返回值不为0,因此我在写读卡函数的时候会判断是否返回的成功标志为0,如果不为0,就会throw。可是我发现我用多线程后,如果把读卡函数单独的放到一个子线程中,如果读卡函数执行过程中出错,并且throw后会出现主程序直接退出的情况。,并且子线程的异常也没有在主程序界面抛出,希望大家能给说下,我这样用子线程应该如何来避免这种主程序直接退出的情况,对使用者来言太不友好了。我也是最近接触多线程的,谢谢大家的帮忙。

   
//定义个委托
private delegate void Read_Card_info();

/// <summary>
/// 通过委托去执行读卡函数
/// </summary>
private void Read_Info()
{
Invoke(new Read_Card_info(New_recadcard));
}

private void New_recadcard()
{

try
{
//调用服务跟银行交互,获取卡片相关信息
}
catch (System.Exception ex)
{
throw new Exception("读卡片信息错误:" + + ex.ToString());
}

}

//读卡按钮
private void btn_readcard_Click(object sender, EventArgs e)
{
this.ReadCardInfo();
}






在写帖子的时候自己想了一下,是不是我在主线程开辟子线程执行的时候,没有在主线程中获取子线程异常导致的?
...全文
98 3 打赏 收藏 转发到动态 举报
写回复
用AI写文章
3 条回复
切换为时间正序
请发表友善的回复…
发表回复
於黾 2015-01-05
  • 打赏
  • 举报
回复
首先要明确一点,所谓"主线程","子线程",只是一种习惯叫法,它们其实完全是并列的,没有父子关系 所以你在一个线程中把错误直接抛出,轻则该线程死掉,重则主程序死掉,总之一个线程是不会捕获另一个线程里的异常的,需要你自己处理 你主线程里的异常你是怎么处理的,子线程里一样的去处理,是show出来,还是显示在label里,还是写入文件,还是如何 总之你主线程有异常是不会throw的,那么子线程中的异常也不要随便throw
  • 打赏
  • 举报
回复
首先,你要明白,主线程中通过catch是无法直接捕获子线程中的异常的 也就是你上面的Read_Info方法要自己处理异常,你可以定义一个委托(事件)来处理异常 public event ErrorEventHandler Error; public void OnError(Exception exp) { if(this.Error != null) this.Error(this, new ErrorEventArgs(exp)); } private void New_recadcard() { try { //调用服务跟银行交互,获取卡片相关信息 } catch (System.Exception ex) { //throw new Exception("读卡片信息错误:" + + ex.ToString()); //触发处理异常的事件 this.OnError(ex); } } 然后在Form.Load中注册你的事件处理,如: this.Error += (obj, evt) => MessageBox.Show(evt.GetException().Message, "未处理异常");
  • 打赏
  • 举报
回复
代码少写了一部分,现在补上


   
       //定义个委托
        private delegate void Read_Card_info();

        /// <summary>
        /// 通过委托去执行读卡函数
        /// </summary>
        private void Read_Info()
        {
           Invoke(new Read_Card_info(New_recadcard));
        }

      private void New_recadcard()
        {
            
            try
            {
                 //调用服务跟银行交互,获取卡片相关信息
            }
            catch (System.Exception ex)
            {
                throw new Exception("读卡片信息错误:" + + ex.ToString());            
            }
           
        }

      //读卡按钮
       private void btn_readcard_Click(object sender, EventArgs e)
        {
            this.ReadCardInfo();
        }


     public bool ReadCardInfo()
        {
            Thread w = new Thread(new ThreadStart(Read_Info));
            w.Start();

            return true;
        }





110,499

社区成员

发帖
与我相关
我的任务
社区描述
.NET技术 C#
社区管理员
  • C#
  • Web++
  • by_封爱
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

让您成为最强悍的C#开发者

试试用AI创作助手写篇文章吧