本文老周就给大伙伴们介绍一下方法参数代码的生成。

在开始之前,先补充一下上一篇烂文的内容。在上一篇文章中,老周检讨了 MemberAttributes 枚举的用法,老周此前误以为该枚举不能进行按位操作,后来发现是可以的。不过啊,MemberAttributes 枚举有些情况下不那么好弄,最典型的就是要生成抽象类的时候,反正老周试了很久,用MemberAttributes枚举不能顺利生成抽象类。

这时候,老周想到了 TypeAttributes,然后就试了一下。

            CodeTypeDeclaration t = new CodeTypeDeclaration("MyClass");
t.TypeAttributes = System.Reflection.TypeAttributes.Abstract; CodeMemberProperty pry = new CodeMemberProperty();
pry.Name = "A";
pry.Attributes = MemberAttributes.Abstract | MemberAttributes.Public;
pry.Type = new CodeTypeReference(typeof(string));
t.Members.Add(pry); CodeDomProvider p = CodeDomProvider.CreateProvider("cs");
p.GenerateCodeFromType(t, Console.Out, null);

把 TypeAttributes 属性设置为 Abstract ,就可以将类标识为抽象类。而抽象成员则可以将 Attributes 属性直接指定为抽象成员,比如上面例子中的A属性。

然后生成的代码如下图所示。

下面进入本文的要点——生成方法参数。

老周的习惯是,示例学习效率高。所以,我不多说理论的东西,来看例子。

            CodeMemberMethod m = new CodeMemberMethod();
m.Name = "SetData";
m.Attributes = MemberAttributes.Public | MemberAttributes.Final;
// 参数
CodeParameterDeclarationExpression p1 = new CodeParameterDeclarationExpression();
p1.Name = "name";
p1.Type = new CodeTypeReference(typeof(string));
m.Parameters.Add(p1);
CodeParameterDeclarationExpression p2 = new CodeParameterDeclarationExpression();
p2.Name = "city";
p2.Type = new CodeTypeReference(typeof(string));
m.Parameters.Add(p2);
CodeParameterDeclarationExpression p3 = new CodeParameterDeclarationExpression();
p3.Name = "phone";
p3.Type = new CodeTypeReference(typeof(int));
m.Parameters.Add(p3);
CodeCommentStatement cm = new CodeCommentStatement("方法体");
m.Statements.Add(cm); CodeDomProvider provider = CodeDomProvider.CreateProvider("cs");
provider.GenerateCodeFromMember(m, Console.Out, null);

别看这代码貌似有点长,其实就是声明一个方法,然后添加三个参数。参数的声明属于表达式,因此用到CodeParameterDeclarationExpression类,Type属性设置参数的类型。

示例代码中,CodeCommentStatement表示方法体中包含注释。

生成的方法如下图所示。

默认情况下,参数为输入参数,我们知道,还有两种方法参数——输出参数、引用传参。

CodeParameterDeclarationExpression 公开 Direction 属性,专门用于设置参数的方向,输入参数是默认值,因此可以不显式赋值,另外两个值就是Ref和Out。

下面代码将生成一个带有 out 参数的方法。

            CodeMemberMethod m3 = new CodeMemberMethod();
m3.Name = "MakeKey";
// 返回值
m3.ReturnType = new CodeTypeReference(typeof(bool));
// 输入参数
CodeParameterDeclarationExpression pi = new CodeParameterDeclarationExpression(typeof(int), "len");
m3.Parameters.Add(pi);
// 输出参数
CodeParameterDeclarationExpression po = new CodeParameterDeclarationExpression(typeof(byte[]), "res");
po.Direction = FieldDirection.Out; //重点
m3.Parameters.Add(po); Console.WriteLine("VB 代码:");
CodeDomProvider provider = CodeDomProvider.CreateProvider("vb");
provider.GenerateCodeFromMember(m3, Console.Out, null);
Console.WriteLine("\n\nC# 代码:");
provider = CodeDomProvider.CreateProvider("cs");
provider.GenerateCodeFromMember(m3, Console.Out, null);

要让参数变为输出参数,就要把 Direction 属性设置为 Out。

请看结果。

知道如何定义 out 参数,那ref参数就简单了,比如下面例子。

            // 定义类型
CodeTypeDeclaration dt = new CodeTypeDeclaration("MySocket");
// 方法成员
CodeMemberMethod mt = new CodeMemberMethod();
mt.Name = "ReadData";
mt.Attributes = MemberAttributes.Public;
// ref 参数
CodeParameterDeclarationExpression pr = new CodeParameterDeclarationExpression(typeof(System.Net.IPEndPoint), "endpoint");
pr.Direction = FieldDirection.Ref;
mt.Parameters.Add(pr);
dt.Members.Add(mt); CodeDomProvider provider = CodeDomProvider.CreateProvider("cs");
provider.GenerateCodeFromType(dt, Console.Out, null);

生成代码如下。

OK,今天的内容就讲完了,东西不多,也不难。下一篇文章,老周继续厚着脸皮和各位探讨 CodeDom,下一次将介绍一下特性的定义。

【.net 深呼吸】细说CodeDom(6):方法参数的更多相关文章

  1. 【.net 深呼吸】细说CodeDom(7):索引器

    在开始正题之前,先补充一点前面的内容. 在方法中,如果要引用方法参数,前面的示例中,老周使用的是 CodeVariableReferenceExpression 类,它用于引用变量,也适用于引用方法参 ...

  2. 【.net 深呼吸】细说CodeDom(5):类型成员

    前文中,老周已经厚着脸皮介绍了类型的声明,类型里面包含的自然就是类型成员了,故,顺着这个思路,今天咱们就了解一下如何向类型添加成员. 咱们都知道,常见的类型成员,比如字段.属性.方法.事件.表示代码成 ...

  3. 【.net 深呼吸】细说CodeDom(4):类型定义

    上一篇文章中说了命名空间,你猜猜接下来该说啥.是了,命名空间下面就是类型,知道了如何生成命名空间的定义代码,之后就该学会如何声明类型了. CLR的类型通常有这么几种:类.接口.结构.枚举.委托.是这么 ...

  4. Eclipse中自动提示的方法参数都是arg0,arg1的解决方法

    Eclipse中自动提示的方法参数都是arg0,arg1,就不能根据参数名来推断参数的含义,非常不方便. 解决方法:Preferences->Java->Installed JREs,发现 ...

  5. java中方法参数的一些总结(1)

    1.问题说明        在C++中,函数调用时有传值调用和传址调用两种方式,但在Java中只有传值调用一种方式.Java中的方法参数为那几种基本数据类型的情况跟C++中一样,传入的只是变量的拷贝. ...

  6. php课程---Windows.open()方法参数详解

    Window.open()方法参数详解 1, 最基本的弹出窗口代码   window.open('page.html'); 2, 经过设置后的弹出窗口   window.open('page.html ...

  7. Scala正则和抽取器:解析方法参数

    在<正则表达式基础知识>中概括了正则表达式的基础知识, 本文讲解如何使用正则表达式解析方法参数,从而可以根据 DAO 自动生成 Service. 在做 Java 项目时,常常要根据 DAO ...

  8. java方法参数

    Java程序设计语言总是采用值调用.也就是说,方法得到的是所有参数的一个拷贝,特别是方法不能修改传递给它的任何参数变量的内容. 基本类型参数 1)X被初始化为percent值的一个拷贝: 2)X被乘以 ...

  9. 新手容易混乱的String+和StringBuffer,以及Java的方法参数传递方式。

    之前在交流群里和猿友们讨论string+和stringbuffer哪个速度快以及Java的方法参数传递的问题,引起了群里猿友的小讨论.最终LZ得出的结果是string+没有stringbuffer快, ...

随机推荐

  1. Cortex-M3中C与汇编的交互

          以下内容摘自<ARM Cortex-M3权威指南>         概览       在CM3 上编程,既可以使用C 也可以使用汇编.可能还有其它语言的编译器,但是大多数人还是 ...

  2. Execution Order of Event Functions

    In Unity scripting, there are a number of event functions that get executed in a predetermined order ...

  3. 2016- 1- 16 NSThread 的学习

    一:NSThread的概念: 二:NSThread的使用: 1.创建一个Thread 1.1第一种方法: - (void)test1{ NSString *str = @"zhengli&q ...

  4. C#下如何用NPlot绘制期货股票K线图(2):读取数据文件让K线图自动更新

    [内容介绍]上一篇介绍了K线图的基本绘制方法,但很不完善,本篇增加了它直接读取数据的功能,这对于金融市场的数据量大且又需要动态刷新功能的实现很重要. [实现方法] 1.需要一个数据文件,这里用的是直接 ...

  5. uva 10859 - Placing Lampposts dp

    题意: 有n个节点,m条边,无向无环图,求最少点覆盖,并且在同样点数下保证被覆盖两次的变最多 分析: 1.统一化目标,本题需要优化目标有两个,一个最小灯数a,一个最大双覆盖边数b,一大一小,应该归一成 ...

  6. cocos2dx3.0导出自定义类到lua的方法详细步骤

    我写了一个用3.0的工具导出类到lua,自动生成代码的方法. 以前要导出c++类到lua,就得手动维护pkg文件,那简直就是噩梦,3.0以后就会感觉生活很轻松了. 下面我就在说下具体做法.1.安装必要 ...

  7. ascii、unicode、utf-8、gbk 区别

    原文:https://blog.csdn.net/u010262331/article/details/46013905 ASCII:遇上0×10, 终端就换行: 遇上0×07, 终端就向人们嘟嘟叫: ...

  8. SpringCloud服务负载均衡实现原理02

  9. Docker+STF在ubuntu下测试环境搭建(详细搭建步骤及踩坑记录)

    一.什么是OpenSTF? STF又称OpenSTF,它是一个手机设备管理平台,可以对手机进行远程管理.调试.远程手机桌面监控等操作.这个系统类似于目前很流行的云测服务比如Testin,虽然网页上提供 ...

  10. 关于使用CTE(公用表表达式)的递归查询

    --关于使用CTE(公用表表达式)的递归查询 --CTE 的基本语法结构如下: WITH expression_name [ ( column_name [,...n] ) ] AS ( CTE_qu ...