• nlohmann 非侵入式代码生成(llvmcppparser)


    nlohmann是一个用起来很方便的json c++ 库,但是还得自己写一堆代码。特别是如果原来的结构较多,得改一堆,

    可以用llvm cpp parser来生成这样的代码。

    主函数

    static void Main(string[] args)
    {

    var p = @"J:\fy\inc\";
    var files = new List<string>()
    {
    "test.h"
    };
    var fullfns = files.Select(x => p + x).ToList();
    ParseSourceFile(fullfns);


    }

    具体的代码如下:

    public static bool ParseSourceFile(List<string> files)
    {
    // Lets setup the options for parsing the file.
    var parserOptions = new ParserOptions
    {
    LanguageVersion = LanguageVersion.CPP17,
    Verbose = true
    };

    parserOptions.Setup();

    var parserResult = ClangParser.ParseSourceFiles(files, parserOptions);

    if (parserResult.Kind != ParserResultKind.Success)
    {
    if (parserResult.Kind == ParserResultKind.FileNotFound)
    Console.Error.WriteLine("some file was not found.");

    for (uint i = 0; i < parserResult.DiagnosticsCount; i++)
    {
    var diag = parserResult.GetDiagnostics(i);

    Console.WriteLine("{0}({1},{2}): {3}: {4}",
    diag.FileName, diag.LineNumber, diag.ColumnNumber,
    diag.Level.ToString().ToLower(), diag.Message);
    }

    parserResult.Dispose();
    return false;
    }

    var astContext = ClangParser.ConvertASTContext(parserOptions.ASTContext);
    parserResult.Dispose();

    foreach (var unit in astContext.TranslationUnits)
    {
    if (unit.IsSystemHeader)
    continue;
    foreach (var ns in unit.Namespaces)
    {
    HandleNamespace(ns, ns.LogicalName);
    }
    }
    return true;
    }

    public static void HandleClass(Class cls, string nsname)
    {
    if (!nsname.StartsWith("fy::"))
    {
    Console.WriteLine("not fy msg:"+nsname+"::"+cls.Name);
    return;
    }
    var rosns = nsname.Substring(4);
    StringBuilder sb_fromros = new StringBuilder();
    sb_fromros.AppendLine("template<>");
    sb_fromros.AppendFormat("FYMSG_DECL void copy_from_ros({0}::{1} &lhs, const {2}::{1} &rhs)", nsname, cls.Name,
    rosns);
    sb_fromros.AppendLine("{");
    foreach (var mem in cls.Fields)
    {
    var fldname = mem.Name;
    sb_fromros.AppendFormat(" copy_from_ros(lhs.{0}, rhs.{0});\n", fldname);
    }

    sb_fromros.AppendLine("}");


    StringBuilder sb_tojson = new StringBuilder();
    sb_tojson.AppendLine("template<>");
    sb_tojson.Append(
    $"FYMSG_DECL void to_json(nlohmann::json &js, const {nsname}::{cls.Name} &t)\n");
    sb_tojson.AppendLine("{");
    foreach (var mem in cls.Fields)
    {
    var fldname = mem.Name;
    sb_tojson.AppendFormat(" to_json(js[\"{0}\"], t.{0});\n", fldname);
    }

    sb_tojson.AppendLine("}");

    StringBuilder sb_fromjson = new StringBuilder();
    sb_fromjson.AppendLine("template<>");
    sb_fromjson.Append(
    $"FYMSG_DECL void from_json(const nlohmann::json &js, {nsname}::{cls.Name} &t)\n");
    sb_fromjson.AppendLine("{");
    foreach (var mem in cls.Fields)
    {
    var fldname = mem.Name;
    sb_fromjson.AppendFormat(" from_json(js[\"{0}\"], t.{0});\n", fldname);
    }

    sb_fromjson.AppendLine("}");

    Console.WriteLine(sb_fromros.ToString());
    Console.WriteLine();
    Console.WriteLine(sb_tojson.ToString());
    Console.WriteLine();
    Console.WriteLine(sb_fromjson.ToString());
    }

    public static void HandleNamespace(Namespace ns, string fullns)
    {
    var clses = ns.Classes;
    foreach (var cls in clses)
    HandleClass(cls, fullns);
    foreach (var subns in ns.Namespaces)
    {
    string newfullns = fullns + "::" + subns.LogicalName;
    HandleNamespace(subns, newfullns);
    }
    }

    如果序列化不是用的这个,同理可以在里面处理,其实就是通过cpp parser 拉到他的所有field,然后生成对应的代码。

  • 相关阅读:
    认识v$fixed_view_definition
    V$、GV$、X$、V_$、GV_$之间的关系
    ORACLE OEM
    ORACLE表空间
    linux
    系统数据库备份恢复
    linux -- #!/bin/bash
    linux -- ubuntu 脚本开机自启动
    linux -- chown修改文件拥有者和所在组
    php -- php控制linux关机、重启、注销
  • 原文地址:https://www.cnblogs.com/sevencatwang/p/16053443.html
Copyright © 2020-2023  润新知