美文网首页
重构一个库的过程

重构一个库的过程

作者: ww4u | 来源:发表于2018-03-08 15:57 被阅读0次

    为什么需要重构

    • 维护困难
    • 维护困难是由多方面因素所引起的,例如命名规则,处理过程,算法实现等

    怎样实现

    格式化

    • 格式化的目的是为了能集中注意力,不至于因为糟糕的格式影响读代码的心情

    去掉全局变量

    • 因为是作为库进行发布的,如果作为全局变量很有可能和其他名称相冲突
    • 解决的方法:
      • 变量由外部传入,即整个处理过程对于外部调用方是完全可控的,没有内部的隐含输入
      • 将内部的API使用static进行包含
      • 将整个库放置到单独的命名空间中(这需要语言的支持)

    审核库中对于资源的申请和释放

    • 对于资源的把控是嵌入式程序员的必修课,所以见到malloc/new等就会自然的反应,free/delete呢?所以,一见到库中有大量的new而且见不到delete时,自己是不敢使用这个库的
    double** J = new double*[6];
    
    • 解决的方法
      • 对于需要传回的资源,由外部传入空间,不允许在callee中进行资源的申请
      • 善于使用栈上的空间,在新版的C类编译器中是可以支持可变数组的定义的,这样就省去了小空间从堆上分配的麻烦
    double localRads[ angleCount ];
    

    重新封装API

    • 库中所定义的API的过程处理痕迹明显,所以面对巨大的数组,内心是崩溃的。诚然,使用这种内存布局的好处就是便于在ABI的层次进行兼容。
    res.P1 = tempP[j][0];
            res.P2 = tempP[j][1];
            res.P3 = tempP[j][2];
            res.P4 = tempP[j][3];
            res.V1 = tempV[j][0];
            res.V2 = tempV[j][1];
            res.V3 = tempV[j][2];
    
    • 解决的方法:
      • 定义结构,利用语言的特性做一定的伪装(为了说明,我隐去了结构和变量名称),通过这种形式进行适配。
    struct xxxXXX
    {
        union {
            struct {
            double x[4];
            double xx[4];
            double xxx;
            };
    
            double datas;
        };
    };
    
    • 为了不污染全局空间,将库代码放置到命名空间再进行编译
    namespace xxx
    {
    #include "outlib.cpp"
    }
    

    统一错误返回

    • 对于可能失败的过程,定义统一的错误规则,
      例如:0表示成功,其他表示错误。
      为什么使用0?因为0太特殊了,不需要过多的说明和注释就能注意到

    增加配置项

    • 库中的常数使用宏定义或由外部进行配置

    整理代码结构

    • 简练整洁的代码赏心悦目
    • 代码不仅是自己看的,后来人也会看。只有自己能看得懂的程序,不是优秀的程序。(如果自己都看不懂的程序,那就是垃圾)

    添加注释

    • 注释不再多,而在精
    • 完美的程序不需要注释的,我们都是凡人,写不出完美的程序,所以注释是必不可少的
    • 注释能自然地概括处理过程,便于从高层次上理解程序的实现

    测试

    • 测试前,需要多读几遍代码,逐个审阅各分支,循环等控制逻辑
    • 重构的前提是能够正常工作
    • 所以,需要进行单步的测试,确保正确性

    相关文章

      网友评论

          本文标题:重构一个库的过程

          本文链接:https://www.haomeiwen.com/subject/kbjyfftx.html