熱點推薦:
您现在的位置: 電腦知識網 >> 編程 >> .NET編程 >> 正文

c#中通過值和引用傳遞參數

2013-11-13 10:07:40  來源: .NET編程 

  在 C# 中既可以通過值也可以通過引用傳遞參數通過引用傳遞參數允許函數成員(方法屬性索引器運算符和構造函數)更改參數的值並保持該更改若要通過引用傳遞參數請使用 ref 或 out 關鍵字為簡單起見本主題的示例中只使用了 ref 關鍵字有關 ref 和 out 之間的差異的信息請參見使用 ref 和 out 傳遞數組

  本主題包括下列章節


傳遞值類型參數
傳遞引用類型參數

  它還包括以下示例


示例 演示 是否使用 ref 或 out 通過值傳遞值類型 否 通過引用傳遞值類型 是 交換值類型(兩個整數) 是 通過值傳遞引用類型 否 通過引用傳遞引用類型 是 交換引用類型(兩個字符串) 是

傳遞值類型參數

  值類型變量直接包含其數據這與引用類型變量不同後者包含對其數據的引用因此向方法傳遞值類型變量意味著向方法傳遞變量的一個副本方法內發生的對參數的更改對該變量中存儲的原始數據無任何影響如果希望所調用的方法更改參數值必須使用 ref 或 out 關鍵字通過引用傳遞該參數為了簡單起見以下示例使用 ref

示例 通過值傳遞值類型

  下面的示例演示通過值傳遞值類型參數通過值將變量 myInt 傳遞給方法 SquareIt方法內發生的任何更改對變量的原始值無任何影響

  // PassingParamscs 
using System;
class PassingValByVal
{
    static void SquareIt(int x)
    // The parameter x is passed by value
    // Changes to x will not affect the original value of myInt
    {
        x *= x;
        ConsoleWriteLine(The value inside the method: {} x);
    }
    public static void Main()
    {
        int myInt = ;
        ConsoleWriteLine(The value before calling the method: {}
           myInt);
        SquareIt(myInt);   // Passing myInt by value
        ConsoleWriteLine(The value after calling the method: {}
           myInt);
    }
}

輸出

  The value before calling the method:
The value inside the method:
The value after calling the method:

代碼討論

  變量 myInt 為值類型包含其數據(值 當調用 SquareIt 時myInt 的內容被復制到參數 x 中在方法內將該參數求平方但在 Main 中myInt 的值在調用 SquareIt 方法之前和之後是相同的實際上方法內發生的更改只影響局部變量 x

示例 通過引用傳遞值類型

  下面的示例除使用 ref 關鍵字傳遞參數以外其余與示例 相同參數的值在調用方法後發生更改

  // PassingParamscs 
using System;
class PassingValByRef
{
    static void SquareIt(ref int x)
    // The parameter x is passed by reference
    // Changes to x will affect the original value of myInt
    {
        x *= x;
        ConsoleWriteLine(The value inside the method: {} x);
    }
    public static void Main()
    {
        int myInt = ;
        ConsoleWriteLine(The value before calling the method: {}
           myInt);
        SquareIt(ref myInt);   // Passing myInt by reference
        ConsoleWriteLine(The value after calling the method: {}
           myInt);
    }
}

輸出

  The value before calling the method:
The value inside the method:
The value after calling the method:

代碼討論

  本示例中傳遞的不是 myInt 的值而是對 myInt 的引用參數 x 不是 int 類型它是對 int 的引用(本例中為對 myInt 的引用)因此當在方法內對 x 求平方時實際被求平方的是 x 所引用的項myInt

示例 交換值類型

  更改所傳遞參數的值的常見示例是 Swap 方法在該方法中傳遞 x 和 y 兩個變量然後使方法交換它們的內容必須通過引用向 Swap 方法傳遞參數否則方法內所處理的將是參數的本地副本以下是使用引用參數的 Swap 方法的示例

  static void SwapByRef(ref int x ref int y)
{
    int temp = x;
    x = y;
    y = temp;
}

  調用該方法時請在調用中使用 ref 關鍵字如下所示

  SwapByRef (ref i ref j);

  傳遞引用類型參數

  引用類型的變量不直接包含其數據它包含的是對其數據的引用當通過值傳遞引用類型的參數時有可能更改引用所指向的數據如某類成員的值但是無法更改引用本身的值也就是說不能使用相同的引用為新類分配內存並使之在塊外保持若要這樣做請使用 ref(或 out)關鍵字傳遞參數為了簡單起見以下示例使用 ref

示例 通過值傳遞引用類型

  下面的示例演示通過值向 Change 方法傳遞引用類型的參數 myArray由於該參數是對 myArray 的引用所以有可能更改數組元素的值但是試圖將參數重新分配到不同的內存位置時該操作僅在方法內有效並不影響原始變量 myArray

  // PassingParamscs 
// Passing an array to a method without the ref keyword
// Compare the results to those of Example 
using System;
class PassingRefByVal 
{
   static void Change(int[] arr)
   {
      arr[]=;   // This change affects the original element
      arr = new int[{    };   // This change is local
      ConsoleWriteLine(Inside the method the first element is: {} arr[]);
   }
   
   public static void Main() 
   {
      int[] myArray = {};
      ConsoleWriteLine(Inside Main before calling the method the first element is: {} myArray []);
      Change(myArray);
      ConsoleWriteLine(Inside Main after calling the method the first element is: {} myArray []);
   }
}

輸出

  Inside Main before calling the method the first element is:
Inside the method the first element is:
Inside Main after calling the method the first element is:

代碼討論

  在上個示例中數組 myArray 為引用類型在未使用 ref 參數的情況下傳遞給方法在此情況下將向方法傳遞指向 myArray 的引用的一個副本輸出顯示方法有可能更改數組元素的內容(從 改為 但是在 Change 方法內使用 new 運算符分配新的內存部分將使變量 arr 引用新的數組因此這之後的任何更改都不會影響原始數組 myArray(它是在 Main 內創建的)實際上本示例中創建了兩個數組一個在 Main 內一個在 Change 方法內

示例 通過引用傳遞引用類型

  本示例除在方法頭和調用中使用 ref 關鍵字以外其余與示例 相同方法內發生的任何更改都會影響調用程序中的原始變量

  // PassingParamscs 
// Passing an array to a method with the ref keyword
// Compare the results to those of Example 
using System;
class PassingRefByRef 
{
   static void Change(ref int[] arr)
   {
      // Both of the following changes will affect the original variables:
      arr[]=;
      arr = new int[{    };
      ConsoleWriteLine(Inside the method the first element is: {} arr[]);
   }
   
   public static void Main() 
   {
      int[] myArray = {};
      ConsoleWriteLine(Inside Main before calling the method the first element is: {} myArray []);
      Change(ref myArray);
      ConsoleWriteLine(Inside Main after calling the method the first element is: {} myArray []);
   }
}

輸出

  Inside Main before calling the method the first element is:
Inside the method the first element is:
Inside Main after calling the method the first element is:

代碼討論

  方法內發生的所有更改都影響 Main 中的原始數組實際上使用 new 運算符對原始數組進行了重新分配因此調用 Change 方法後對 myArray 的任何引用都將指向 Change 方法中創建的五個元素的數組

示例 交換兩個字符串

  交換字符串是通過引用傳遞引用類型參數的很好的示例本示例中str 和 str 兩個字符串在 Main 中初始化並作為由 ref 關鍵字修飾的參數傳遞給 SwapStrings 方法這兩個字符串在該方法內以及 Main 內均進行交換

  // PassingParamscs
using System;
class SwappinStrings
{
    static void SwapStrings(ref string s ref string s)
    // The string parameter x is passed by reference
    // Any changes on parameters will affect the original variables
    {
        string temp = s;
        s = s;
        s = temp;
        ConsoleWriteLine(Inside the method: {} {} s s);
    }
    public static void Main()
    {
        string str = John;
        string str = Smith;
        ConsoleWriteLine(Inside Main before swapping: {} {} 
           str str);
        SwapStrings(ref str ref str);   // Passing strings by reference
        ConsoleWriteLine(Inside Main after swapping: {} {} 
           str str);
    }
}

輸出

  Inside Main before swapping: John Smith
Inside the method: Smith John
Inside Main after swapping: Smith John

代碼討論

  本示例中需要通過引用傳遞參數以影響調用程序中的變量如果同時從方法頭和方法調用中移除 ref 關鍵字則調用程序中不會發生任何更改


From:http://tw.wingwit.com/Article/program/net/201311/12635.html
    推薦文章
    Copyright © 2005-2013 電腦知識網 Computer Knowledge   All rights reserved.