方法的结构
方法是一块具有名称的代码,在类和结构中都经常用到
局部变量
局部变量位于方法内部,在方法中声明时产生,在方法执行结束时结束
类型推断与var关键字
某些情况下,在声明的开始部分包含类型名是多余的,因为可以通过初始化看出是什么类型,所以这时可以统一使用var关键字来声明:
需要注意的是var只能用于局部变量,并且需要附带初始化
嵌套块中的局部变量
这里与C/C++不同的是,C#中即使是嵌套的不同的块也不可以使用相同的局部变量名,嵌套块中局部变量的生存期如下图:
局部常量
需要注意的是,局部常量必须在声明时初始化,且之后值不变。这里的const不是修饰符(如ref、out),而是类型声明的一部分,其他都跟局部变量一致
返回值
通常方法被调用后可以返回一个值,要返回值时需要为方法设置一个返回类型,如果为空则设置为void,返回类型可以是自定义类型。
void方法通常不需要返回语句,但是使用return;提前退出方法块也是常用的方法。
局部函数
也叫做本地函数,意思是可以在函数体内部定义函数,这样的好处是为了简化函数逻辑,因为有事函数本身就是另一个函数的部分逻辑,这部分目前用的比较少。
参数
本节比较重要,且较复杂
形参
形参是局部变量,但是是在方法的参数列表中声明,而不是在块中
实参
在方法调用时用于初始化形参的参数就是实参,实参应与形参类型匹配或可发生隐式转换
值参数
值参数指的是一类函数参数类型,这种类型的特点是直接在栈中复制实参作为形参,为形参分配内存。
当实参为值类型时,因为值参数会拷贝一个副本来执行方法,所以并不会影响值类型的实参;
当实参为引用类型时,值参数会拷贝引用类型的副本,但是此时副本作为地址显然指向同一块堆中的位置,所以此时对形参执行的方法会影响实参的值。
由上面这段代码可见,值类型不受方法影响,而引用类型发生了变化。
注意:这里值类型与值参数要区别开,前者是相对于内存而言的数据项类型,值类型表示类型本身包含其值;而值参数这里表示一种函数的参数类型。
引用参数
使用引用参数时,必须加上ref作为修饰符,且参数应为变量而不是实际值
使用时容易出错的一点是需要在声明和调用时都加上ref
与值参数在栈中为形参分配内存不同,引用参数不会为形参分配内存,而是将形参作为实参的别名
ref返回和ref局部变量
ref局部变量可以为变量创建别名,即使是值类型的变量,这样对原变量和别名的改动都会同步。
声明方式是:
实际上ref局部变量经常与ref返回一起使用。
ref返回使方法返回变量的引用而不是变量值,声明方法为:
ref返回的使用有很多限制:
引用类型作为值参数
引用类型作为值参数时,前面提到了,会复制一份实参的地址,后面也是对实参执行方法,但是如果创建一个新对象并赋值给形参,就会将形参与实参之间的联系转换为形参与新对象之间的联系,并且这个新对象是局部的,在方法执行完毕时就会释放,所以创建新对象并赋值给形参之后就会切断形参与实参的联系。
在方法开始时与前面一致,形参实参都指向堆中同一对象,但当方法分配新对象给形参后就会切断与实参的联系,方法调用之后,形参和新对象都会消失。
引用类型作为引用参数
引用类型作为引用参数时,根据前面的内容,引用参数的形参是实参的别名,所以也是指向堆中同一对象,但当方法分配新对象给形参后,因为形参是实参的别名,实参也会指向新对象,此时形参实参都指向新对象,当方法调用完成后形参消失,实参指向新对象。