当前位置: 代码迷 >> C# >> WinForm中,线程调用已释放部分的有关问题,望帮忙!
  详细解决方案

WinForm中,线程调用已释放部分的有关问题,望帮忙!

热度:128   发布时间:2016-05-05 04:26:27.0
WinForm中,线程调用已释放部分的问题,望各位高手帮忙!!
C# 小弟没有实际经验,虽然很久之前学习过,但是没有经历过现实的项目。目前单位有向C# 方向发展的意向,有个简单的小项目要用C#来实现。其间,用到了线程处理,比较简单的。但是在使用过程中,有个问题,一直不知道怎么来处理,虽然可以避之,也不影响结果。但总觉得是个疙瘩,不是很舒服。

简单描述,登录窗体,通过线程获取管理母卡的卡号,验证结束后,登录软件系统。
其中的处理是,窗体显示,线程启动,得到正确的卡号后,验证通过,关闭线程,关闭窗口。
问题就出在关闭线程,关闭出口中,会提示 “无法访问已释放的对象 w_login”。
做了一些限制,但是只是减少了该情况发生的几率,并没有完全解决掉。
希望大牛能够给个彻底解决的方向,小弟先在此谢谢了!!!!!!


下面是部分代码:
线程中的执行部分
//发送寻卡指令
        private void findCard()
        {
            string strCardCode = "";
            int outTime = 1500; //超时时间
           
            while (bRunMark)    //启动后该变量为true
            {
                //*********************************
                //                     数据处理
                //*********************************
                    if (bRunMark)   //为了防止问题发生 在此做了限定  变量为false
                    {
                        try
                        {
                            this.Invoke((EventHandler)(delegate
                            {
                                if (VariableClass.CheckFormIsOpen("w_login"))  //在此做了 该窗口关闭的限定 如果窗口关闭 此条件即为false
                                {
                                    if (getPerson(strCardCode) == 1) //w_login中的一个自定方法
                                    {
                                        //目的变量赋值
                                    }
                                    else
                                    {
                                        //目的变量赋值
                                    }
                               }
                            }));
                        }
                        catch (Exception ex)
                        {
                            MessageBox.Show("错误:" + ex.Message);
                            return;
                        }
                    }    
            }
        }


准备结束退出窗口的部分
private void btnOk_Click(object sender, EventArgs e)
        {          
                //*********************
                //        数据处理
                //*********************
               
                //成功关闭窗体
                bRunMark = false;
                this.Close();               
            }
        }           

------解决思路----------------------
如果是登陆窗体,用户手动关闭,你就应该结束进程,而不是把主窗体再显示出来

除非你的线程正常走完,验证通过了,这时才应该关闭登陆窗体并显示主窗体
------解决思路----------------------
   //成功关闭窗体       
          bRunMark = false;           
  //在此添加 thread是你的线程对象  等待线程退出后才close窗体
 thread.Join()  
  this.Close();           
------解决思路----------------------
引用:
Quote: 引用:

   //成功关闭窗体       
          bRunMark = false;           
  //在此添加 thread是你的线程对象  等待线程退出后才close窗体
 thread.Join()  
  this.Close();           


非常抱歉,刚刚没太仔细看。thread.Join()和我的延时类似,作用确是截然不同的。
我要找的可能就是这个让线程自然结束的,虽然有时候它会处在电脑进程的不同位置,但是它都会自行结束C#中的线程,不会造成故障。

同上,此贴仍会在下周结贴,不知是否还有其它方式解决此类问题?


线程要安全退出,基本原则就是让线程自行结束,
将bRunMark = false;   不能保证线程立刻退出,
延时的方法不可取,如果在线程的while逻辑中有比较耗时的处理,
那么延时后有可能还没有退出。
使用thread.Join(),耐心等待线程自行结束

 
------解决思路----------------------
用委托的异步方式调用即可
  相关解决方案