none
关于.NET线程锁的提问 RRS feed

  • 问题

  •     public class Class1
        {
            public int aa = 0;
            public void add()
            {
                aa++;
            }
            public void startthread()
            {
                for (int i = 0; i < 100; i++)
                {
                    Thread th1 = new Thread(new ThreadStart(add));
                    th1.Start();
                }
            }
            public static void Main()
            {
                Class1 cc = new Class1();
                cc.startthread();
                MessageBox.Show(cc.aa.ToString());
            }
            
        }
    
    以上代码,多线程内时对变量改值,有可能引起aa变量的没有递增吗? 是不是需要在改变变量的时候加上lock语句?

    由灵
    • 已移动 ThankfulHeartModerator 2011年12月20日 4:53 C# (发件人:.NET Framework 一般性问题讨论区)
    2011年12月20日 3:52

答案

  •     public class Class1
        {
            public int aa = 0;
            public void add()
            {
                aa++;
            }
            public void startthread()
            {
                for (int i = 0; i < 100; i++)
                {
                    Thread th1 = new Thread(new ThreadStart(add));
                    th1.Start();
                }
            }
            public static void Main()
            {
                Class1 cc = new Class1();
                cc.startthread();
                MessageBox.Show(cc.aa.ToString());
            }
            
        }
    
    以上代码,多线程内时对变量改值,有可能引起aa变量的没有递增吗? 是不是需要在改变变量的时候加上lock语句?

    由灵


    因为多个线程操作一个共享的变量,线程之间是异步的。因此会产生同时操作一个变量,导致前一个线程来不及加后一个线程涌入了,发生错误。

    解决方案——使用Lock。

    namespace A
    {
        public class Class1
        {
            private int aa = 0;

            public int Aa
            {
                get { return aa; }
                set { aa = value; }
            }
            private object obj = new object();
            public void add()
            {
                lock (obj)
                {
                    aa++;
                }
            }
            public void startthread()
            {
                for (int i = 0i < 100i++)
                {
                    Thread th1 = new Thread(new ThreadStart(add));
                    th1.Start();
                }
            }
            public static void Main()
            {
                Class1 cc = new Class1();
                cc.startthread();
                Console.WriteLine(cc.Aa);
            }

        }

    }

     


       QQ我:讨论(Talk)
    下载MSDN桌面工具(Vista,Win7)
    我的博客园
    慈善点击,点击此处
    2011年12月20日 4:51
    版主

全部回复

  •     public class Class1
        {
            public int aa = 0;
            public void add()
            {
                aa++;
            }
            public void startthread()
            {
                for (int i = 0; i < 100; i++)
                {
                    Thread th1 = new Thread(new ThreadStart(add));
                    th1.Start();
                }
            }
            public static void Main()
            {
                Class1 cc = new Class1();
                cc.startthread();
                MessageBox.Show(cc.aa.ToString());
            }
            
        }
    
    以上代码,多线程内时对变量改值,有可能引起aa变量的没有递增吗? 是不是需要在改变变量的时候加上lock语句?

    由灵


    因为多个线程操作一个共享的变量,线程之间是异步的。因此会产生同时操作一个变量,导致前一个线程来不及加后一个线程涌入了,发生错误。

    解决方案——使用Lock。

    namespace A
    {
        public class Class1
        {
            private int aa = 0;

            public int Aa
            {
                get { return aa; }
                set { aa = value; }
            }
            private object obj = new object();
            public void add()
            {
                lock (obj)
                {
                    aa++;
                }
            }
            public void startthread()
            {
                for (int i = 0i < 100i++)
                {
                    Thread th1 = new Thread(new ThreadStart(add));
                    th1.Start();
                }
            }
            public static void Main()
            {
                Class1 cc = new Class1();
                cc.startthread();
                Console.WriteLine(cc.Aa);
            }

        }

    }

     


       QQ我:讨论(Talk)
    下载MSDN桌面工具(Vista,Win7)
    我的博客园
    慈善点击,点击此处
    2011年12月20日 4:51
    版主
  • dear

    锁定物件不建议使用this,请参考以下

    http://www.dotblogs.com.tw/yc421206/archive/2011/01/07/20624.aspx


    秘訣無它,唯勤而已 http://www.dotblogs.com.tw/yc421206/
    2011年12月20日 6:38
  • dear

    锁定物件不建议使用this,请参考以下

    http://www.dotblogs.com.tw/yc421206/archive/2011/01/07/20624.aspx


    秘訣無它,唯勤而已 http://www.dotblogs.com.tw/yc421206/

    Sorry,已经改正代码了。
       QQ我:讨论(Talk)
    下载MSDN桌面工具(Vista,Win7)
    我的博客园
    慈善点击,点击此处
    2011年12月20日 6:40
    版主
  • 多谢! You are right!
    由灵
    2011年12月20日 6:47
  • 多谢! You are right!
    由灵


    不用谢!请顺便标记MVP为答案。他提醒了我粗心的部分。

    另外:希望多多参与MSDN活动,多多帮助别人,同时自己也可以受益匪浅!


       QQ我:讨论(Talk)
    下载MSDN桌面工具(Vista,Win7)
    我的博客园
    慈善点击,点击此处
    2011年12月20日 6:49
    版主
  • dear all

    我相信会来这里讨论问题的都是有心向上的,互相讨论是好事,

    另外再提供一个思路,锁定只要锁定写入的部份,读取不用锁,这样可以增加读取的效能。


    秘訣無它,唯勤而已 http://www.dotblogs.com.tw/yc421206/
    2011年12月20日 9:32