Natasha 高级编译类 (五)- 第一部分
模板类的使用,便于快速生成相关的class类,感觉是基础单元(AssemblyCSharpBuilder)的封装
类名 | 作用 | 命名空间 | 操作类型 |
---|---|---|---|
NAssembly | 快速创建同程序集的 oop 及委托等操作类 | 全局 | 静态初始化,动态实例化 |
NInstance | 根据类型,提供一个初始化实例的委托 | 全局 | 静态 |
NDelegate | 快速创建指定域的 Action/Func 委托 | 全局 | 静态初始化,动态实例化 |
NClass | 快速创建一个公有类 | 全局 | 静态初始化,动态实例化 |
NInterface | 快速创建一个公有接口 | 全局 | 静态初始化,动态实例化 |
NEnum | 快速创建一个枚举类 | 全局 | 静态初始化,动态实例化 |
NRecord | 快速创建一个记录类 | 全局 | 静态初始化,动态实例化 |
NStruct | 快速创建一个结构体 | 全局 | 静态初始化,动态实例化 |
FakeMethodOperator | 仿造 MethodInfo 创建方法 | Natasha.CSharp | 静态初始化,动态实例化 |
FastMethodOperator | 快速创建方法 | Natasha.CSharp | 静态初始化,动态实例化 |
NClass
感觉该类的使用频率会比较高
注意:NClass可以通过获得Method后在进行方法调用,或者实例化以后
使用自带方法进行创建
NatashaManagement.Preheating();
using (NatashaManagement.CreateDomain("Test").CreateScope()){
// 创建class
NClass builder = NClass.UseScope();
var type = builder
// 不包含全局using
.NoGlobalUsing()
// 隐藏命名空间
.HiddenNamespace()
// 类的访问权限
.Access(AccessFlags.Public)
// 名称
.Name("Demo5")
// 带参构造函数
.Ctor(item => item.Public().Param<int>("test").Body("int _test = test;"))
// 属性
.Field(item => { item.Public().Name("Age").Type<int>(); })
// 属性
.Field(item => { item.Public().Name("Name").Type<string>(); })
// 封装的方法
.Property(item => { item.Public().Name("Obj").Type<NClass>(); })
.GetType();
var script = builder.AssemblyBuilder.SyntaxTrees[0].ToString();
System.Console.WriteLine(script);
}
运行结果
另外附上一个较为全面的例子
//构建二 使用了上面例子的type
//添加了该引用一直无效果,因此直接将TestAttribute放到了代码中
NatashaManagement.AddGlobalReference(typeof(TestAttribute));
NClass builder2 = NClass.UseScope();
var type2 = builder2
.Public()
// 类名称
.Name("Demo51")
// 注释
.Summary("This is a test class;")
// 添加只读的int变量ReadonlyField
.PublicReadonlyField<int>("ReadonlyField")
// 声明一个构造函数
.Ctor(item => item.Public().Body("ReadonlyField = 10;"))
// 私有变量声明
.PrivateField<string>("_name", "[TestAttribute]")
// 声明了TestAttribute属性的Get方法
.Property(item => item
.Public()
.Attribute<TestAttribute>()
.Type<string>()
.Name("NameProperty")
.OnlyGetter("return _name;"))
// Get/Set方法
.Property(item => item
.Public()
.Type("AnotherClass")
.Name("AnotherProperty"))
// 名为SetName,参数为string的返回值为_name的虚方法
.Method(item => item
.Public()
.Virtrual()
.Async()
.Name("SetName")
.Param<string>("name")
.Body(@"_name = name;
return _name;")
.Return<Task<string>>())
// 在命名空间中额外添加一个AnotherClass方法
.NamespaceBodyAppend("public class AnotherClass{}")
.NamespaceBodyAppend("public class TestAttribute : Attribute { }")
.GetType();
var script2 = builder2.AssemblyBuilder.SyntaxTrees[0].ToString();
// 打印
System.Console.WriteLine(script2);
运行结果
NEnum
枚举类
//没啥好说的。。。。
NEnum builder = NEnum.DefaultDomain();
var type = builder
.NoGlobalUsing()
.HiddenNamespace()
.Access(AccessFlags.Public)
.Name("EnumDemo")
.EnumField("Apple", 1, "苹果")
.EnumField("Orange", 2)
.EnumField("Banana", 4)
.GetType();
System.Console.Write(builder.AssemblyBuilder.SyntaxTrees[0].ToString());
运行结果
NRecord
应该是快速生成C# 9 的Record类型
NRecord builder = NRecord.DefaultDomain();
var type = builder
.HiddenNamespace()
.AttributeAppend("[StructLayout(LayoutKind.Explicit)]")
.Access(AccessFlags.Public)
.Name("RecordTest")
.Field(item => { item.AttributeAppend<FieldOffsetAttribute>("0").Public().Name("Apple").Type<int>(); })
.Field(item => { item.AttributeAppend<FieldOffsetAttribute>("0").Public().Name("Orange").Type<int>(); })
.GetType();
System.Console.WriteLine(builder.AssemblyBuilder.SyntaxTrees[0].ToString());
执行结果
未完待续。。。