8.6.3 输出参数——关键字:out

输出参数和引用参数有一定程度的类似,输出参数用于将值从方法内传递到方法外。要使用输出参数只需要将引用参数的ref关键字替换为out关键字即可,但有一点必须注意的是,只有变量才有资格作为输出参数,文本值和表达式都不可以,这点要谨记。好了,我们来看一个例子,里面有引用参数和输出参数,大家可以做个对比,然后再看看它们的运行结果有何异同。如代码清单8-12所示。

代码清单8-12 输出参数


1 using System;

2 public class MethodSample

3{

4 public static void Main()

5{

6 MethodSample ms=new MethodSample();

7 int x=5;

8 string s=“猜猜我会被改变吗?”;

9 ms.DoSomething(ref x,out s);

10 Console.WriteLine("x={0},s={1}",x,s);

11}

12

13 public void DoSomething(ref int someValue1,out string someValue2)

14{

15//Console.WriteLine(someValue1);

16//Console.WriteLine(someValue2);

17 someValue1=10;

18 someValue2=“我确实被改变了”;

19}

20}


是不是形式很相似?再看运行结果:


x=10,s=我确实被改变了


咦?这和代码清单8-10的运行结果完全一样!是不是就可以认为输出参数和引用参数除了关键字不同以外,其实就是一个东西?且慢!请读者将代码清单8-12自行录入电脑,分别将第15、16行注释去掉,运行两次,看看两次结果是否相同。亲自动手做过实验的读者就能发现,去掉第15行的注释能正常编译运行,而去掉第16行的注释则编译都无法通过,编译器发出如下错误信息:

使用了未赋值的out参数"someValue2"

这说明两个问题:

❑编译器允许在方法中的任意位置、任意时刻读取引用参数的值;

❑编译器禁止在为输出参数赋值前读取它。

这意味着输出参数的初始值基本上是没意义的,因为它在使用前要被赋为新的值。因此,想通过输出参数将值传入方法的路是行不通的。

这次,我们将代码清单8-11使用输出参数改写,来看看会是怎样的结果,它和前面按引用传递有何异同。如代码清单8-13所示。

代码清单8-13 使用输出参数示例


1 public class MethodSample

2{

3 public static void Main()

4{

5 MethodSample ms=new MethodSample();

6 Rectangle rectangle=null;

7 int myValue;

8 ms.CalculateArea(out rectangle,out myValue);

9}

10

11 public void CalculateArea(out Rectangle rect,out int value)

12{

13 Rectangle tmpRect=new Rectangle();

14 tmpRect.Length+=10;

15 tmpRect.Width+=15;

16 tmpRect.Area=tmpRect.Length*tmpRect.Width;

17 rect=tmpRect;

18 value=15;

19}

20}

21

22 public class Rectangle

23{

24 public int Length=10;

25 public int Width=15;

26 public int Area;

27}


大家仔细观察代码清单8-13和代码清单8-11,除了下划线部分不同以外,还有什么不同?结果我们将稍后揭晓,按照惯例,现在我们使用图8-11来揭示代码背后的事实。

8.6.3 输出参数——关键字:out - 图1

图 8-11 使用输出参数图示

现在揭晓答案,见表8-4。

8.6.3 输出参数——关键字:out - 图2