Natasha 4.0 discovery path series template API

Posted by yaron on Wed, 26 Jan 2022 01:12:21 +0100

Natasha template

Natasha encapsulates the compilation unit and provides a variety of templates to help developers build functions
The premise of using the API in this article is that you are familiar with C# and know enough about some types of system
Therefore, Natasha will refuse the issue related C# to popular science. Please understand
Existing templates:

Template name purpose
NClass Build type script
NStuct Build structure script
NEnum Build enumeration script
NInterface Build interface script
NRecord Build record script
NDelegate Quickly create delegates
FastOperator Quickly create operation classes for methods
FakeOperator Method to copy the operation class

usage method

Create class

//Constant preheating for ten thousand years
NatashaInitializer.Preheating();

//Create a type in a random field
NClass builder = NClass.RandomDomain();

var type = builder
    .Public()
    .Summary("This is a test class;")
    /*
     namespace NatashaDynimacSpace
     {
       /// <summary>
       /// This is a test class;
       /// </summary>
       public class Nee7e202ee18c413dacae62af6b106c6e
    */


    .PublicReadonlyField<int>("ReadonlyField")
    //public readonly System.Int32 ReadonlyField;


    .Ctor(item => item.Public().Body("ReadonlyField = 10;"))
    /*
     public Nee7e202ee18c413dacae62af6b106c6e()
     {
              ReadonlyField = 10;
     }
    */


    .PrivateField<string>("_name", "[MyTestAttribute]")
    //[MyTestAttribute]
    //private System.String _name;


    .Property(item => item
        .Public()
        .Attribute<MyTestAttribute>()
        .Type<string>()
        .Name("NameProperty")
        .OnlyGetter("return _name;"))
     /*[NatashaFunctionUT.Template.Compile.MyTestAttribute]
     public System.String NameProperty
     {
            get
            {
                return _name;
            }
     }*/


    .Property(item => item
        .Public()
        .Type("AnotherClass")
        .Name("AnotherProperty"))
    //public AnotherClass AnotherProperty { get; set; }


    .Method(item => item
        .Public()
        .Virtrual()
        .Async()
        .Name("SetName")
        .Param<string>("name")
        .Body(@"_name = name;return _name;")
        .Return<Task<string>>())
     /*
      public virtual async System.Threading.Tasks.Task<System.String> SetName(System.String name)
      {
            _name = name;
            return _name;
      }
    */

    .NamespaceBodyAppend("public class AnotherClass{}")
    /*
     public class AnotherClass
     {
     }
    */
    .GetType();

Create structure

//Create the following structure
/*
[StructLayout(LayoutKind.Explicit)]
public struct EnumUT1
{
    [System.Runtime.InteropServices.FieldOffsetAttribute(0)]
    public System.Int32 Apple;
    [System.Runtime.InteropServices.FieldOffsetAttribute(0)]
    public System.Int32 Orange;
}";
*/
NStruct builder = NStruct.RandomDomain();
           
var type = builder
  .HiddenNamespace()
  .AttributeAppend("[StructLayout(LayoutKind.Explicit)]")
  .Access(AccessFlags.Public)
  .Name("EnumUT1")
  .Field(item => { item.AttributeAppend<FieldOffsetAttribute>("0").Public().Name("Apple").Type<int>(); })
  .Field(item => { item.AttributeAppend<FieldOffsetAttribute>("0").Public().Name("Orange").Type<int>(); })
  .GetType();
var script = builder.AssemblyBuilder.SyntaxTrees[0].ToString();

Create enumeration

//Create the following enumeration
/*
public enum EnumUT1
{
    /// <summary>
    /// Apple
    /// </summary>
    Apple = 1,
    Orange = 2,
    Banana
}
*/
NEnum builder = NEnum.RandomDomain();
           
var type = builder
  .NoGlobalUsing()
  .HiddenNamespace()
  .Access(AccessFlags.Public)
  .Name("EnumUT1")
  .EnumField("Apple", 1,"Apple")
  .EnumField("Orange", 2)
  .EnumField("Banana")
  .GetType();
var script = builder.AssemblyBuilder.SyntaxTrees[0].ToString();

Create interface

//Create the following interfaces
/*
using System;

public interface Interface1
{
    System.String Abc { get; set; }

    System.Int32 Test(System.String p);
}
*/

var builder = NInterface.RandomDomain();
var type = builder
    .NoGlobalUsing()
    .HiddenNamespace()
    .Access(AccessFlags.Public)
    .Name("Interface1")
    .Property(item => item.Type<string>().Name("Abc"))
    .Method(item => item.Name("Test").Param<string>("p").Return<int>())
    .GetType();
var script = builder.AssemblyBuilder.SyntaxTrees[0].ToString();

Quickly create delegates using NDelegate

NDelegate implements the creation method of custom delegate / system delegate (action & func)
The parameter name / parameter type / return value of the delegate corresponds to the system delegate one by one
For system delegates, if you don't know the corresponding parameter name when adding a method body, you can F12 to the corresponding Action/Func definition to view the parameter name

The following is an example of common system delegate parameter names

  • The parameter name defined by action < T1 > is obj; The action < T1, T2 > parameter names are: arg1, arg2;
  • The parameter name defined by func < T1, R > is Arg; Func < T1, T2, R > parameter names: arg1, arg2;

Use code:

  • Usage 1: Custom delegate
public delegate int TestDelegate(string value);
var action = NDelegate
              .RandomDomain()
              .Delegate<TestDelegate>(@"return (value+""hello"").Length;");
int result = action("Hello");
  • Usage 2: system delegation
var action = NDelegate
              .RandomDomain()
              //Create unmanaged asynchronous delegation, corresponding system delegation: func < string, string, task < string > >
              .UnsafeAsyncFunc<string, string, Task<string>>(@"return arg1 +"" ""+ arg2;");

string result = await action("Hello", "World1!");
Assert.Equal("Hello World1!", result);

In addition, I will upload some strange constructs in this directory, including some new technology applications and interesting semantic extensions UT link

Other API s

Compared with basic construction, templates not only provide convenient chain API, but also use management

  • NoGlobalUsing()/UseGlobalUsing(): whether to use the default (global) domain (used by default)
  • LoadDomainUsing()/NotLoadDomainUsing(): whether to load using in the random domain where the template is located (used by default)

ending

In fact, Natasha template is the basic encapsulation for most C# of the data types. You can further customize the encapsulation. For example, you can create a Web COntroller template based on NClass. If you need other extensions, you can first understand the source code structure or discuss the extension with me

Topics: C#