Ref and Out Parameters Questions
我原以为我明白其中的区别,但现在我不太确定。我已经看了几遍技术答案,但我不明白发生了什么。我有这个例子。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 | class Program { static void Main() { int val = 0; Example1(val); Console.WriteLine(val); // Still 0! Example2(ref val); Console.WriteLine(val); // Now 2! Example3(out val); Console.WriteLine(val); // Now 3! } static void Example1(int value) { value = 1; } static void Example2(ref int value) { value = 2; } static void Example3(out int value) { value = 3; } } |
我一直认为默认参数之间的区别是,如果我将val传递到example1中,就不能使用赋值。
但是使用ref关键字val仍然是0,但是我已经创建了一个引用,它现在在example2(ref val)中被视为变量"value"。到目前为止我有什么事要挂断吗?如果我曾经用过
1 2 3 | int value = 0; Example1(value); Console.WriteLine(value); // this would then return 1 correct? |
现在,out关键字发生了什么?和裁判一样?
好的,这是评论中链接问题的副本,但我会尽力为您解释。
未修饰参数
案例A:
-或
案例B:
在案例A中,参数是值类型,默认情况下,值类型作为原始值的副本传递给函数。这并不意味着不允许您修改该值,但该值不会在调用位置反射回来。这对于所有值类型都是相同的,值在传递给函数之前会被复制。
在案例B中,参数是引用类型。这些类型在默认情况下按原样传递。它们不会被复制,但不允许您更改引用(通过将
REF关键字
案例A:
-或
案例B:
在案例A中,您告诉编译器您希望通过引用传递值,这意味着编译器不会复制类型,而是传递对该类型的引用。允许函数更改它。
在案例B中,您告诉编译器允许函数更改引用指向的位置(您可以创建一个
out关键字
案例A:
-或
案例B:
这里,您基本上是为函数定义额外的返回类型。它是一个方法参数,告诉调用者期望结果出现在
看看这是否有帮助:
没有"装饰家"
1 2 3 4 5 6 7 8 9 10 11 12 | static void Example(int value) { Console.WriteLine("Value is {0}", value); value = 99; } usage { int value = 10; Example(notADefaultValue); // Will print <Value is 10> Console.WriteLine("Value is {0}", value); // will print <Value is 10> } |
摘要:默认情况下,值类型(structs/enums/int/double/etc)不会作为引用传入,因此对方法中的变量所做的任何操作都不会影响调用方。因此,"ref"关键字。如果您将一个引用类型传递给一个方法(即一个类),并改变它的内部结构,这些将影响调用者。
默认参数:
1 2 3 4 5 6 7 8 9 10 11 | static void Example(int value = 5) { Console.WriteLine("Value is {0}", value); } usage { int notADefaultValue = 10; Example(notADefaultValue); // Will print <Value is 10> Example(); // will print <Value is 5> } |
摘要:默认值允许您在不显式地需要传递参数的情况下调用方法,使用默认值。
参考参数:
1 2 3 4 5 6 7 8 9 10 11 12 | static void Example(ref int value) { Console.WriteLine("Value is {0}", value); value = 99; } usage { int value = 10; Example(ref value); // Will print <Value is 10> Console.WriteLine("Value is {0}", value); // Will print <Value is 99> } |
摘要:如果将值类型作为引用(reference)传入,则值本身会发生更改。默认情况下,所有引用类型都作为引用传入。仅供参考,int是一个基元类型,因此需要一个显式的"ref"。
输出参数:
1 2 3 4 5 6 7 8 9 10 11 12 | static void Example(out int value) { value = 99; Console.WriteLine("Value is {0}", value); } usage { int value; // no need to init it Example(out value); // Will print <Value is 99> Console.WriteLine("Value is {0}", value); // Will print <Value is 99> } |
摘要:out参数类似于返回变量,但通过方法的签名传入。最常见的例子是typarse,其中方法返回重要信息,根据该信息,out参数是有效的还是无效的(如果为真,则有效)。
在第一个示例中,您没有指定变量是引用,因为它是基本类型,所以它只复制提供的数字。因此,
第二个示例使用引用。这意味着函数
在第三个示例中,