c# 方法:分布、扩展、匿名和普通方法

c# 方法:分布、扩展、匿名和普通方法
一.概述:
万事万物皆对象,孙悟空是个对象,他会摘桃子,是一种行为,这种行为就是c#中的方法,方法是有指定功能的代码块。说起方法就得说一下方法的签名:修饰符、返回值类型、方法参数。在定义方法时的参数叫“形式参数(形参)”,在调用方法时的参数叫“实际参数(实参)”。
这些基本了解之后,下面开始谈几类方法:分布、扩展、匿名和普通方法。

二.分布方法:
要说分布方法要先说分布类:在Visual Studio中创建一个Windows窗体应用程序,打开窗体Form1的代码部分和Form1.Designer.cs 文件,如图

Form1类的修饰符有个partial关键字,没错,partial关键字就是表示此类或此方法为分布类或分布方法的,上面的例子把分布类或分布方法的好处已经体现了:可以让一个类分布在多个文件,这样就可以让多个程序员编写了,也可以让一个类的几个功能块分布在多个文件中。
注意:
a.partial关键字只能修饰类、结构或方法。分布方法只能存在于分布类或分布结构中。
b.partial是Visual Studio的关键字,不是C#语法的关键字。在最终编译的时候,分布类会统一编译成一个类,如果分布方法未提供该实现,则会在编译时移除方法以及对方法的所有调用。
c.各个部分必须具有相同的可访问性,如 public、private 等。
d.如果将任意部分声明为抽象的,则整个类型都被视为抽象的,如果将任意部分声明为密封的,则整个类型都被视为密封的,如果任意部分声明基类型,则整个类型都将继承该类。指定基类的所有部分必须一致,但忽略基类的部分仍继承该基类型,各个部分可以指定不同的基接口,最终类型将实现所有分部声明所列出的全部接口。
e.分部方法声明必须以上下文关键字 partial 开头,并且方法必须返回 void。
f.分部方法可以有 ref 参数,但不能有 out 参数。
g.分部方法为隐式 private 方法,因此不能为 virtual 方法。
h.分部方法不能为 extern 方法,因为主体的存在确定了方法是在定义还是在实现。
i.分部方法可以有 static 和 unsafe 修饰符。
j.分部方法可以为泛型的。约束将放在定义分部方法声明上,但也可以选择重复放在实现声明上。参数和类型参数名称在实现声明和定义声明中不必相同。
k.不能将委托转换为分部方法。

三.扩展方法:
扩展方法使您能够向现有类型“添加”方法,而无需创建新的派生类型、重新编译或以其他方式修改原始类型。
扩展方法必须是静态的,第一个参数指定该方法作用于哪个类型,并且该参数以 this 修饰符为前缀。举例说明:
namespace HelloWorld
{
using IamExtend;
class Program
{
static void Main(string[] args)
{
string str = “hello world”;
Console.WriteLine(str.IamExt());//hello world,I am Extend
}
}
}
namespace IamExtend
{
static class ExtString
{
public static string IamExt(this string str)
{
str += “,I am Extend”;
return str;
}
}
}
细心的话会有一个疑问:IamExt是静态方法,而在调用的时候是变量str点出来的,能用变量点出来的方法不是实例化方法吗?在这里,不是!扩展方法是一种特殊的静态方法,但在代码中可以像扩展类型上的实例方法一样进行调用,实际上,编译器生成的中间语言 (IL) 会将代码转换为对静态方法的调用。
深入思考一下:类有封装性,而上例中的string是由微软定义,并且已经封装,而扩展类ExtString和string并没有继承关系,那么既然string已经封装,但现在还可以为它增加方法,是不是违反了类的封装性呢?不是!实际上,扩展方法无法访问它们所扩展的类型中的私有变量,扩展方法对它们所扩展的类型中的所有所有成员相互之间无异常,所扩展的类型中的方法或属性是public的能访问,是private还是不能访问,不干扰,无影响。
注意:
a.如果扩展方法与该类型中定义的方法具有相同的签名,则扩展方法永远不会被调用。
b.扩展方法被放在命名空间级别放入范围中。例如,如果您在同一个名为 Extensions 的命名空间中具有多个包含扩展方法的静态类,则这些扩展方法将全部由 using Extensions; 指令放入范围中。

四.匿名方法:
1.先看一个例子:

匿名方法就是dText = delegate() { Console.WriteLine(“hello world”); };等号右边的。说一下专业名词:如果局部变量和参数的范围包含匿名方法声明,则该局部变量和参数称为该匿名方法的“外部”变量
2.匿名方法的定义就不多说了,注意:
a.匿名方法的参数的范围是“匿名方法块”。
b.如果目标在块外部,那么,在匿名方法块内使用跳转语句(如 goto、break 或 continue)是错误的。如果目标在块内部,在匿名方法块外部使用跳转语句(如 goto、break 或 continue)也是错误的。
c.与局部变量不同,捕获变量的生命周期一直持续到引用该匿名方法的委托符合垃圾回收的条件为止。
d.匿名方法不能访问外部范围的 ref 或 out 参数。
e.在“匿名方法块”中不能访问任何不安全代码。
f.在 is 运算符的左侧不允许使用匿名方法。

五.普通方法:
1.程序的Main方法:
a.Main方法比较特殊,它是程序入口点。
b.Main方法的签名只有四种:
static void Main(string[] args)
static void Main()
static int Main(string[] args)
static int Main()
2.值类型参数方法和引用类型参数方法:
这两种方法都是经常用的,比如说有个int i参数的方法,那么它就是值类型参数方法;有个Button button的参数的方法,那么它就是引用类型参数方法。
3.out关键字参数方法和ref关键字参数方法:
a.out关键字参数方法:
static void Main(string[] args)
{
int i=1;
Text(out i);
Console.WriteLine(i);//10
}
static void Text(out int i) { i = 10;}

由上例可以看出变量I的值变了,这就是out关键字参数方法的效果。
注意:
对于out关键字参数方法,方法体中要用该out修饰的变量,必须先赋值!
b.ref关键字参数方法:
static void Main(string[] args)
{
int i=1;
Text(ref i);
Console.WriteLine(i);
//结果:
//1
//10
}
static void Text(ref int i)
{
Console.WriteLine(i);
i = 10;
}

上例中,在Text方法中并没有给变量I赋值,就可以打印I,这是跟out关键字参数方法很大的区别
c.区别:
out关键字参数方法:只出
ref关键字参数方法:也进也出
4.params关键字参数方法:
a.使用:
static void Main(string[] args)
{
Text(1,2,3);
//结果:
//1
//2
//3
}
static void Text(params int[] i)
{
foreach (int j in i)
{
Console.WriteLine(j);
}
}

b.方法的唯一性:
static void Main(string[] args)
{
int i=1;
Text(1);
//结果:
//1.1
}
static void Text(int i)
{
Console.WriteLine(“1.”+i);
}
static void Text(params int[] i)
{
foreach (int j in i)
{
Console.WriteLine(i);
}

    }

在方法static void Text(int i)和static void Text(params int[] i)只有一个参数的时候,以static void Text(int i)为准,因为它有唯一性。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值