• juggle添加c#版本


    此前做过一个c++版的网络层dsl:http://www.cnblogs.com/qianqians/p/4255034.html

    现在给这个dsl加入c#的支持,并且对代码的结构做了优化,将语法解析和代码生成做了解耦

    语法解析部分

    class func(object):
        def __init__(self):
            self.keyworld = ''
            self.func = []
            self.argvtuple = None
    
        def clear(self):
            self.keyworld = ''
            self.func = []
            self.argvtuple = None
    
        def push(self, ch):
            if ch == ' ' or ch == '':
                self.keyworld = deleteNoneSpacelstrip(self.keyworld)
                if self.keyworld != '':
                    if self.argvtuple is None:
                        self.func.append(deleteNoneSpacelstrip(self.keyworld))
                    else:
                        if self.keyworld in ['table', 'array', 'int', 'string', 'float', 'bool']:
                            self.argvtuple.append(deleteNoneSpacelstrip(self.keyworld))
                    self.keyworld = ''
                return False
    
            if ch == ',':
                if self.keyworld != '' and self.keyworld in ['table', 'array', 'int', 'string', 'float', 'bool']:
                    self.argvtuple.append(deleteNoneSpacelstrip(self.keyworld))
                    self.keyworld = ''
    
                return False
    
            if ch == '(':
                self.keyworld = deleteNoneSpacelstrip(self.keyworld)
                if self.keyworld != '':
                    self.func.append(deleteNoneSpacelstrip(self.keyworld))
                self.argvtuple = []
                self.keyworld = ''
                return False
    
            if ch == ')':
                if self.keyworld != '' and self.keyworld in ['table', 'array', 'int', 'string', 'float', 'bool']:
                    self.argvtuple.append(deleteNoneSpacelstrip(self.keyworld))
    
                if self.argvtuple is None:
                    self.func.append([])
                else:
                    self.func.append(self.argvtuple)
    
                self.keyworld = ''
                return False
    
            if ch == ';':
                return True
    
            self.keyworld += ch
    
            return False
    
    class module(object):
        def __init__(self):
            self.keyworld = ''
            self.name = ''
            self.module = []
            self.machine = None
    
        def push(self, ch):
            if ch == '}':
                self.machine = None
                return True
    
            if self.machine is not None:
                if self.machine.push(ch):
                    self.module.append(self.machine.func)
                    self.machine.clear()
            else:
                if ch == '{':
                    self.name = deleteNoneSpacelstrip(self.keyworld)
                    self.keyworld = ''
                    self.machine = func()
                    return False
    
                self.keyworld += ch
    
            return False
    
    class statemachine(object):
        def __init__(self):
            self.keyworld = ''
            self.module = {}
            self.machine = None
    
        def push(self, ch):
            if self.machine is not None:
                if self.machine.push(ch):
                    if isinstance(self.machine, module):
                        self.module[self.machine.name] = self.machine.module
                        self.machine = None
            else:
                if ch == ' ' or ch == '':
                    if deleteNoneSpacelstrip(self.keyworld) == 'module':
                        self.machine = module()
                        self.keyworld = ''
                else:
                    self.keyworld += ch
    
        def getmodule(self):
            return self.module
    
        def syntaxanalysis(self, genfilestr):
            for str in genfilestr:
                for ch in str:
                    self.push(ch)

    解析采用状态机机制,逐字符读取代码在读取到关键字符则跳转状态,并且保持读取到的关键字。

    读取的关键字采用table方式保持

    module:[funcinfo, ...]

    在代码生成部分,按解析获取的语法table生成module和caller代码,分别是事件的响应和调用端。

    def gencaller(module_name, funcs):
            code = "/*this caller file is codegen by juggle*/
    "
            code += "using System;
    "
            code += "using System.Collections;
    "
            code += "using System.IO;
    "
            code += "using MsgPack;
    "
            code += "using MsgPack.Serialization;
    
    "
    
            code += "namespace caller
    "
            code += "{
    "
            code += "    public class " + module_name + " : Icaller 
    "
            code += "    {
    "
            code += "        public " + module_name + "(Ichannel _ch) : base(_ch)
    "
            code += "        {
    "
            code += "            module_name = "" + module_name + "";
    "
            code += "        }
    
    "
    
            for i in funcs:
                    code += "        public void " + i[1] + "("
                    count = 0
                    for item in i[2]:
                            code += tools.gentypetocsharp(item) + " argv" + str(count)
                            count = count + 1
                            if count < len(i[2]):
                                    code += ","
                    code += ")
    "
                    code += "        {
    "
                    code += "            ArrayList _argv = new ArrayList();
    "
                    for n in range(len(i[2])):
                            code += "            _argv.Add(argv" + str(n) + ");
    "
                    code += "            call_module_method("" + i[1] + "", _argv);
    "
                    code += "        }
    
    "
    
            code += "    }
    "
            code += "}
    "
    
            return code
    def genmodule(module_name, funcs):
        code = "/*this module file is codegen by juggle*/
    "
        code += "using System;
    "
        code += "using System.Collections;
    
    "
    
        code += "namespace module
    {
    "
        code += "    public class " + module_name + " : Imodule 
        {
    "
    
        code += "        public " + module_name + "()
            {
    "
        code += "            module_name = "" + module_name + "";
    "
        code += "        }
    
    "
    
        for i in funcs:
            code += "        public abstract void " + i[1] + "("
            count = 0
            for item in i[2]:
                code += tools.gentypetocsharp(item) + " argv" + str(count)
                count = count + 1
            code += ");
    
    "
    
        code += "    }
    "
        code += "}
    "
    
        return code

    和juggle的上个版本不同,为了简洁的用于开发游戏服务器,这个版本删除了同步调用功能,只保留异步调用,对同步调用感兴趣的 可以阅读darckforce里面的代码:https://github.com/qianqians/darkforce/tree/master/juggle

    这个版本的代码地址在:https://github.com/qianqians/abelkhan

    我将基于这个版本的juggle开发一个开源的游戏服务器框架,欢迎大家在论坛或博客给我留言提出意见

  • 相关阅读:
    opencv 编译
    uniapp中使用xgplayer直播、讨论区的简单实现、第三方复制功能
    20192422李俊洁 实验八 Web安全
    PaddleSpeech 安装(ubuntu 20.04)并尝鲜其中的 TTS 功能
    webstorm 自动导入时始终使用单引号
    音视频字幕生成和翻译
    PaddleSpeech TTS 资料汇总
    vue中更新两个不相关组件的方法
    vue关闭ESlint
    两个数组 过滤出另一个数组中的值的方法
  • 原文地址:https://www.cnblogs.com/qianqians/p/5634178.html
Copyright © 2020-2023  润新知