從0自學C#13--子類和父類方法的鎖對象問題

來源:互聯網
上載者:User
調用父類方法時,如何與子類方法,在鎖對象不是同一個執行個體下,能安全執行緒,請見下面三種情況。

case1:

如下代碼,在調用父類的方法時,和子類的方法,發生安全執行緒問題。原因的鎖對象的執行個體不是同一個。

using System;using System.Collections.Generic;using System.Linq;using System.Text;using System.Threading.Tasks;using System.Threading;namespace ForTest//check the lock object for thread safety{    class Program    {        static void Main(string[] args)        {            son myson = new son();            Parallel.For(0, 5, (int i) =>             {                 myson.methodA();                 myson.methodC();             });            Console.ReadKey();        }    }    public class grandfather    {        //protected static object syncRoot = new object();    }    public class father:grandfather    {        private static object syncRoot = new object();        protected int cont = 0;        public virtual bool methodA()        {            lock (syncRoot)            {                cont++;                Thread.Sleep(1000);                Console.WriteLine("cout++ is " + cont);                return true;            }        }        public virtual bool methodB()        {            lock (syncRoot)            {                return true;            }        }    }    public class son:father    {        private static object syncRoot = new object();        public bool methodC()        {            lock (syncRoot)            {                cont += 2;                Thread.Sleep(2000);                Console.WriteLine("cont += 2 is " + cont);                return true;            }        }    }}

輸出:

cout++ is 1cout++ is 4cont += 2 is 5cout++ is 5cout++ is 8cont += 2 is 9cout++ is 11cont += 2 is 11cont += 2 is 13cont += 2 is 15

case2:

case1的解決方案是,在父類初始化鎖對象,讓子類繼承。這樣就安全執行緒了。如下。

using System;using System.Collections.Generic;using System.Linq;using System.Text;using System.Threading.Tasks;using System.Threading;namespace ForTest//check the lock object for thread safety{    class Program    {        static void Main(string[] args)        {            son myson = new son();            Parallel.For(0, 5, (int i) =>             {                 myson.methodA();                 myson.methodC();             });            Console.ReadKey();        }    }    public class grandfather    {        protected static object syncRoot = new object();    }    public class father:grandfather    {        protected int cont = 0;        public virtual bool methodA()        {            lock (syncRoot)            {                cont++;                Thread.Sleep(1000);                Console.WriteLine("cout++ is " + cont);                return true;            }        }        public virtual bool methodB()        {            lock (syncRoot)            {                return true;            }        }    }    public class son:father    {        public bool methodC()        {            lock (syncRoot)            {                cont += 2;                Thread.Sleep(2000);                Console.WriteLine("cont += 2 is " + cont);                return true;            }        }    }}

輸出:

cout++ is 1cout++ is 2cont += 2 is 4cout++ is 5cout++ is 6cout++ is 7cont += 2 is 9cont += 2 is 11cont += 2 is 13cont += 2 is 15

case3:

當然有些特殊情況下,子類硬要重新執行個體化一個鎖對象。如何避免上面第一種安全執行緒問題發生?需要:

子類加鎖重寫父類分方法(如果父類methodA是虛方法)

或者

new一下(如果父類methodA是執行個體方法)。

using System;using System.Collections.Generic;using System.Linq;using System.Text;using System.Threading.Tasks;using System.Threading;namespace ForTest//check the lock object for thread safety{    class Program    {        static void Main(string[] args)        {            son myson = new son();            Parallel.For(0, 5, (int i) =>             {                 myson.methodA();                 myson.methodC();             });            Console.ReadKey();        }    }    public class grandfather    {        protected static object syncRoot = new object();    }    public class father:grandfather    {        protected int cont = 0;        public virtual bool methodA()        {            lock (syncRoot)            {                cont++;                Thread.Sleep(1000);                Console.WriteLine("cout++ is " + cont);                return true;            }        }        public virtual bool methodB()        {            lock (syncRoot)            {                return true;            }        }    }    public class son:father    {        private static object sync = new object();        public override bool methodA()//重寫        {            lock (sync)            {                return base.methodA();            }        }        public bool methodC()        {            lock (sync)            {                cont += 2;                Thread.Sleep(2000);                Console.WriteLine("cont += 2 is " + cont);                return true;            }        }    }}

 public new bool methodA()\\new一下        {            lock (sync)            {                return base.methodA();            }        }

輸出:

cout++ is 1cout++ is 2cont += 2 is 4cout++ is 5cout++ is 6cout++ is 7cont += 2 is 9cont += 2 is 11cont += 2 is 13cont += 2 is 15

以上就是 從0自學C#13--子類和父類方法的鎖對象問題的內容,更多相關內容請關注topic.alibabacloud.com(www.php.cn)!

  • 相關文章

    聯繫我們

    該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

    如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

    A Free Trial That Lets You Build Big!

    Start building with 50+ products and up to 12 months usage for Elastic Compute Service

    • Sales Support

      1 on 1 presale consultation

    • After-Sales Support

      24/7 Technical Support 6 Free Tickets per Quarter Faster Response

    • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.