編程細(xì)節(jié)|你的if缺少了一個(gè)else

今天踩了一個(gè)if-else的坑。

事故現(xiàn)場(chǎng):

程序結(jié)構(gòu)如圖:


struct.png

采用偽代碼表述:

        /**
         * 服務(wù)器傳過(guò)來(lái)值:1或者2
         * 客戶端根據(jù)傳值修改變量:水果狀態(tài)1或者2
         * 
         * 函數(shù)()
         * {
         *      水果=null;
         *     
         *      if(水果狀態(tài)==1)
         *      {
         *          水果=new 蘋果();
         *      }
         *      elseif(水果狀態(tài)==2)
         *      {
         *          水果=new 獼猴桃();
         *      }
         *  
         *      水果.打印();
         *}
         */

程序一直好好地運(yùn)行著。直到某一天,某同學(xué)觸發(fā)了服務(wù)器某個(gè)機(jī)關(guān),服務(wù)器不斷的給客戶端發(fā)送這條消息,然后客戶端就崩掉了。

事故還原:

用線程不斷修改key來(lái)模擬服務(wù)器傳遞過(guò)來(lái)的消息,主線程添加一個(gè)臨時(shí)變量,來(lái)打印東西。代碼如下:

        public static int Key = 1;      //根據(jù)key值打印不同的數(shù)據(jù)
        //線程1不斷修改key值為1
        public static void ChangeKey()
        {
            while (true)
            {
                Key = 1;
            }
        }    
        //線程1不斷修改key值為2
        public static void ChangeKey2()
        {
            while (true)
            {
                Key = 2;
            }
        }
        //根據(jù)key值打印不同的字符串
        public static void PrintStr()
        {
            string  str = "空值";
            if (Key==1)
            {
                str = "現(xiàn)在key是1";
            }
            else if (Key == 2)
            {
                str = "現(xiàn)在key是2";
            }
            Console.WriteLine(str);
        }
        //主函數(shù)
        static void Main(string[] args)
        {
            //開啟兩個(gè)線程
            Thread thread1 = new Thread(new ThreadStart(ChangeKey));
            Thread thread2 = new Thread(new ThreadStart(ChangeKey2));
            thread1.Start();
            thread2.Start();
            Thread.Sleep(50);

            //主線程執(zhí)行50次打印函數(shù)
            int i = 0;
            while (i<=50)
            {
                i++;
                PrintStr();
            }
        }

猜測(cè)一下打印的東西都是什么?


if_else.gif

Key值只有1,2兩種情況啊,判斷語(yǔ)句要么執(zhí)行第一句,要么執(zhí)行第二句,怎么可能出現(xiàn)空值呢。顯然if-else出了問(wèn)題。

事故分析:

其實(shí)上述例子跟文章開頭的事故還是有一定的差別的。但是出問(wèn)題的原因是一樣的。先說(shuō)例子,多線程之間的資源共享,或者說(shuō)資源搶占導(dǎo)致的。具體看圖片流程:


first.png

接著下一步:


second.png

問(wèn)題出現(xiàn)了。再說(shuō)開局的例子,根據(jù)服務(wù)器傳送過(guò)來(lái)的狀態(tài)執(zhí)行函數(shù),本身就相當(dāng)于多線程。因此在if-else的空隙,導(dǎo)致“水果=null”,接著再用“水果.打印()”就發(fā)生了崩潰的情況。

小結(jié):

當(dāng)然解決辦法有很多種,要根據(jù)自身項(xiàng)目需求來(lái)定。這里只是提幾個(gè)編程細(xì)節(jié):
1.變量初始化即給初值,盡量避免使用null;
2.if和else配對(duì)使用;
3.變量使用前盡量判空。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

友情鏈接更多精彩內(nèi)容