2010-05-29 53 views
4

我写了一些关于ref -out声明的代码块。我认为裁判是最有用的。好。为什么我需要用掉。我可以每次总是使用参考:为什么必须使用“out”而不是ref?

namespace out_ref 
{ 
    class Program 
    { 
     static void Main(string[] args) 
     { 
      sinifA sinif = new sinifA(); 
      int test = 100; 
      sinif.MethodA(out test); 
      Console.WriteLine(test.ToString()); 

      sinif.MethodB(ref test); 
      Console.WriteLine(test.ToString()); 
      Console.ReadKey(); 
     } 
    } 

    class sinifA 
    { 

     public void MethodA(out int a) 
     { 
      a = 200; 
     } 

     int _b; 
     public void MethodB(ref int b) 
     { 
      _b = b; 
      b = 2*b; 
     } 
    } 

} 

回答

13

是的,你可以每次使用ref,但他们有不同的目的。 ref用于参数既是输入又是输出。当参数仅为输出时使用out。它可以用来传递输入,但是它使得函数的用户在使用函数之前不需要声明实例,因为实际上你会保证创建实例。当您从集合中获取值时,它在TryXXX模式中特别有用

+3

此外,一个出参数必须由需要它的函数初始化,否则你会得到编译错误,这是一件好事。 – 2010-05-29 19:53:03

+0

调用者需要声明变量,但不需要初始化它。 – TrueWill 2010-05-29 21:49:46

6

当您有一个连接了out的参数时,在将它传递给方法之前不需要对它进行初始化接受它。

The out keyword causes arguments to be passed by reference. 
This is like the ref keyword, except that ref requires that the variable be initialized 
before it is passed. 

来自:http://msdn.microsoft.com/en-us/library/ee332485.aspx

3

out参数是保证功能期间被初始化。这为您的呼叫者提供了更严格的合同。它也允许你写这样的代码:

int i; 
MyFunc(out i); 
.. < use i > .. 

没有得到未初始化变量的编译器错误。

0

Out参数

除了通过引用传递值,还可以指定一个给定的参数是一个出 参数通过使用out关键字,其被以相同的方式用作ref关键字(作为函数定义和函数调用中的参数的修饰符 )。实际上,这几乎给出了与参考参数几乎相同的行为 ,因为 函数执行结束时的参数值返回给函数调用中使用的变量。但是,也有重要的 差异:

  1. 虽然是违法使用未分配的变量作为ref参数,你可以使用一个 未赋值的变量作为out参数
  2. out参数必须被视为由使用它的函数取消赋值。

这意味着虽然允许在调用代码时使用指定的变量作为输出参数,但当函数执行时,存储在此变量中的值将丢失。

作为示例,考虑对前面显示的MaxValue()函数的扩展,该函数返回数组的最大值 。稍微修改该函数,以便获取数组中最大值的元素 的索引。为了简单起见,当存在多个具有最大值的元素时,只需获取该值的第一个 的索引。要做到这一点,则通过修改函数如下添加 out参数:

static int MaxValue(int[] intArray, out int maxIndex) 

{ INT MAXVAL = intArray [0]; maxIndex = 0;对于(int i = 1; i < intArray.Length; i ++) { if(intArray [i]> maxVal) { maxVal = intArray [i]; maxIndex = i; } } return maxVal; }

您可以使用此功能如下所示:

int[] myArray = {1, 8, 3, 6, 2, 5, 9, 3, 0, 2}; 

INT maxIndex; (“myArray中的最大值是{0}”, MaxValue(myArray,out maxIndex)); Console.WriteLine(“此值的第一次出现在元素{0}”处, maxIndex + 1);

这导致以下:

在myArray的最大值为9

该值的第一次出现是在元件7

一个已被添加到该在屏幕上显示时,此处返回的maxIndex值。这是 索引转换为一个更可读的形式,以使阵列中的第一个元素被称为元件 1,而不是元素0

1

refout的处理相同的方式在内部,它们'都是通过引用传递一个变量。

区别在于初始化语义,谁负责确保变量具有有效的起始值,并且由编译器执行。

使用out参数,这是您调用的方法。在调用方法之前,通过引用传递的变量中的值是无关紧要的。如果您调用的方法的执行路径无法为其参数设置新值,编译器会发出抱怨。这意味着,在调用方法之前,变量中的任何值都将被覆盖,即使它具有相同的值。

ref参数,这是调用的方法。变量的值将传递给被调用的方法,然后可以检查其参数并可以选择更改它。编译器会在调用之前抱怨调用没有使用值初始化变量的方法。

所以基本上,这完全取决于编译器会抱怨什么。它是调用代码,必须确保变量中有值或者是调用代码。

相关问题