日本好好热aⅴ|国产99视频精品免费观看|日本成人aV在线|久热香蕉国产在线

  • <cite id="ikgdy"><table id="ikgdy"></table></cite>
    1. 西西軟件下載最安全的下載網(wǎng)站、值得信賴的軟件下載站!

      首頁編程開發(fā)C#.NET → c# 引用類型方法參數(shù)的關(guān)鍵字ref深度解析

      c# 引用類型方法參數(shù)的關(guān)鍵字ref深度解析

      相關(guān)軟件相關(guān)文章發(fā)表評(píng)論 來源:西西整理時(shí)間:2012/11/21 14:46:13字體大。A-A+

      作者:西西點(diǎn)擊:0次評(píng)論:0次標(biāo)簽: 引用類型

      昨天在壘代碼的時(shí)候遇到了一個(gè)基礎(chǔ)沒打牢就會(huì)暴露的問題。傳遞給方法的參數(shù)為類(class)時(shí),在方法中所做的修改賦值不一定會(huì)最終改變到原始的變量上。

      舉一個(gè)例子,如果一個(gè)方法Action(List<int> lst),在方法里面對(duì)lst做了很多操作,包括add,remove,new,add等等。傳入變量List<int> input,方法執(zhí)行完之后,input可能被執(zhí)行了add,remove,但是new以后的任何操作都沒有保留。這是為什么呢?最開始學(xué)習(xí).net基礎(chǔ)的時(shí)候就知道,引用類型,傳遞給方法的是引用的地址,而不是實(shí)際數(shù)值。那為什么會(huì)部分的操作被保留了出來,而部分又沒有執(zhí)行呢?

      用代碼來分析此案例:

      static void Main(string[] args)
      {   
          int i = 0;
          int refI = 0;
          List<int> list = new List<int>() { 0, 1, 2 };
          List<int> refList = new List<int>() { 0, 1, 2 };
          testStruct(i);
          TestRefStruct(ref refI);
          TestClass(list);
          TestRefClass(ref refList);
          Console.WriteLine("i: {0}\r\nrefI: {1}\r\nlist: {2}\r\nrefList: {3}", i, refI,
            list.Select(x => x.ToString()).Aggregate((x, y) => x + "," + y),
            refList.Select(x => x.ToString()).Aggregate((x, y) => x + "," + y));
          Console.ReadKey();
      }

      static void TestStruct(int input)
      {
          input = 10;
      }

      static void TestRefStruct(ref int input)
      {
          input = 10;
      }

      static void TestClass(List<int> input)
      {
          input.Add(5);
          input = new List<int>();
          input.Add(10);
      }

      static void TestRefClass(ref List<int> input)
      {
          input.Add(5);
          input = new List<int>();
          input.Add(10);
      }

      調(diào)試程序,最后輸出

      i: 0
      refI: 10
      list: 0,1,2,5
      refList: 10

      在函數(shù)TestStruct中,傳入一個(gè)值類型的參數(shù),沒有對(duì)傳遞進(jìn)去的參數(shù)i做任何的修改。

      在函數(shù)TestRefStruct中,傳入值類型的參數(shù),通過引用傳遞參數(shù)ref,函數(shù)中對(duì)input進(jìn)行的任何改變都影響到了refI上,所做的編輯修改全部保留過來。最終refI的值為10。

      在函數(shù)TestClass中,傳入一個(gè)引用類型的參數(shù),在函數(shù)中,對(duì)input重新賦值之前所做的修改都保留了下來,影響了list的值。而在對(duì)input重新賦值之后的所有修改編輯,都和list沒有任何關(guān)聯(lián)了。

      在函數(shù)TestRefClass中,傳入一個(gè)引用類型的參數(shù),同時(shí),參數(shù)前面加上ref的約束,函數(shù)中,對(duì)input進(jìn)行的任何編輯都影響了refList。最終refList的值為new List<int>{ 10 }。

      有一定.net基礎(chǔ)的人都可以很清晰的理解第一、二和第四種情況。但是第三種情況常常會(huì)給我們留下陷阱。

      如何理解和正確的對(duì)待函數(shù)傳遞的參數(shù)為引用類型的情況?我的理解是:

      第三種情況下,傳遞給函數(shù)的變量A提供的是一個(gè)引用地址,函數(shù)會(huì)自動(dòng)生成一個(gè)變量B,同時(shí)用傳遞進(jìn)來的引用地址對(duì)這個(gè)變量B賦值,這時(shí),傳遞進(jìn)來的變量A和函數(shù)內(nèi)調(diào)用的變量B共一個(gè)引用地址,所做的修改會(huì)同步的影響另一個(gè)參數(shù)。如果在函數(shù)內(nèi)部,出現(xiàn)了一個(gè)input = new List<int>();的語句。這時(shí),變量B會(huì)重新賦值到另一個(gè)引用地址。那么,從此之后,變量B與變量A再?zèng)]有關(guān)聯(lián),對(duì)變量B所做的任何修改將不影響變量A。

      下面模擬代碼呈現(xiàn):

      List<int> A = new List<int>() { 0, 1, 2 };//傳遞給函數(shù)的變量。

      {//進(jìn)入函數(shù)
          List<int> B = A;//函數(shù)執(zhí)行后,自動(dòng)生成B,同時(shí)用A對(duì)B賦值。
          B.Add(5);//由于他們是引用類型,共一個(gè)引用地址,所做修改相互影響。此時(shí)A的值也一起改變。
          B = new List<int>();//對(duì)B重新賦值,指向另一個(gè)引用地址。與A無關(guān)。
          B.Add(10);//A不變。
      }//出函數(shù),B釋放,A繼續(xù)存在。

      個(gè)人理解。如果不足請(qǐng)補(bǔ)充。

        相關(guān)評(píng)論

        閱讀本文后您有什么感想? 已有人給出評(píng)價(jià)!

        • 8 喜歡喜歡
        • 3 頂
        • 1 難過難過
        • 5 囧
        • 3 圍觀圍觀
        • 2 無聊無聊

        熱門評(píng)論

        最新評(píng)論

        第 2 樓 北京市零度聚陣銀河世紀(jì)網(wǎng)吧 網(wǎng)友 客人 發(fā)表于: 2013/5/6 11:17:24
        好高深的東東

        支持( 0 ) 蓋樓(回復(fù))

        第 1 樓 重慶市忠縣 網(wǎng)友 客人 發(fā)表于: 2013/7/14 11:16:57
        繼續(xù)加油

        支持( 0 ) 蓋樓(回復(fù))

        發(fā)表評(píng)論 查看所有評(píng)論(0)

        昵稱:
        表情: 高興 可 汗 我不要 害羞 好 下下下 送花 屎 親親
        字?jǐn)?shù): 0/500 (您的評(píng)論需要經(jīng)過審核才能顯示)