您的位置:首页 > 其它

CheckForIllegalCrossThreadCalls=false;的不安全性

2013-10-12 14:04 1016 查看
我举个线程间不安全的例子,或许对线程间安全理解更深刻一些

   private void button1_Click(object sender, EventArgs e)

        {

            System.Threading.Thread thread1 = new System.Threading.Thread(new System.Threading.ThreadStart(threadfun1));

            thread1.Start();

        }

        void threadfun1()

        {

            double dNumber=0;

            if (double.TryParse(txtNumber.Text, out dNumber) == true)

            {

                double dReciprocal = 1 / Convert.ToDouble(Convert.ToDouble(txtNumber.Text));

                txtNumber.Text = dReciprocal.ToString();

            }
        }

txtNumber是一个文本框,输入一个数,点击按钮后使用线程算出其倒数

如果是多个线程的话,执行if (double.TryParse(txtNumber.Text, out dNumber) == true)还没有问题

但是执行double dReciprocal = 1 / Convert.ToDouble(Convert.ToDouble(txtNumber.Text));可能就出问题了,

因为这段时间txtNumber.Text值可能己经被其它线程改成0了,0没有倒数数,就会出错。(当然使用dNumber也不会出错)

使用代理后

        private void button1_Click(object sender, EventArgs e)

        {

            System.Threading.Thread thread1 = new System.Threading.Thread(new System.Threading.ThreadStart(threadfun1));

            thread1.Start();

        }

        void threadfun1()

        {

            funReciprocal(txtNumber.Text);

        }

    

        delegate void dltReciprocal(string strNumber);

        void funReciprocal(string strNumber)

        {

            if (txtNumber.InvokeRequired)
            {

//由线程调用时txtNumber.InvokeRequired为真,进入这里

                dltReciprocal evtReciprocal = new dltReciprocal(funReciprocal);

                txtNumber.Invoke(evtReciprocal, new object[] { strNumber });//Invoke的作用是执行权交到txtNumber的所有者来执行(在所有者线程中排队执行)。因为代理函数在所有者线程中排队执行,因此不会出现函数没有执行完,UI变量被更新的情况。

            }

            else
            {

//由所有者(窗体)调用时txtNumber.InvokeRequired为假,进入这里

                double dNumber = 0;

                if (double.TryParse(txtNumber.Text, out dNumber) == true)

                {

                    double dReciprocal = 1 / Convert.ToDouble(txtNumber.Text);

                    txtNumber.Text = dReciprocal.ToString();

                }

            }

        }
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息