panda ID:pandaxcl
78814次访问,排名1141好友0人,关注者1
pandaxcl的文章
原创 61 篇
翻译 0 篇
转载 0 篇
评论 151 篇
pandaxcl的公告

博客文档资源下载在本人的网站下载!!!

我也优先在我的网站论坛上面回答问题

在研究C++自动化编程好久之后,发现C++自动化编程在国内还是一个空白。所谓的C++自动化编程,简单点说就是采用了C++的高级模板技术配合产生式编程技法实现了C++代码的自我配置,自动维护代码之间的种种一致性问题。关于这个问题的讨论,将会在我的网站上面进行细致的讨论。如果有问题,欢迎来我的网站提问哦。看看下面的我的网站的链接。

EMail:pandaxcl@163.com

QQ:56637059

我的网站: http://www.autodev.net

最近评论
huxi043715:博主,在很强阿。你的文章也很容易懂。
wangwei200508:呵呵,谢了
您的这里指到自己硬盘了
<a href="file:///D:/work/lex_yacc/chapter01/lexyacc.rar.png" target="_top">这里</a>
imath:老大我引用了你的 这系列文章,嘿嘿
dlr0987:abc* = ab (c+|e) =ab|abc|abcc.....

pandaxcl:这里要注意那个return i
前置和后置都是为了实现增一的效果;)
特意实现前置和后置都是相同的功能的;)
文章分类
收藏
    相册
    友情连接
    小熊猫
    我的另外一个博客
    我的网站-自动化编程社区
    我的论坛-自动化编程社区论坛
    存档
    软件项目交易
    订阅我的博客
    XML聚合  FeedSky
    订阅到鲜果
    订阅到Google
    订阅到抓虾
    订阅到BlogLines
    订阅到Yahoo
    订阅到GouGou
    订阅到飞鸽
    订阅到Rojo
    订阅到newsgator
    订阅到netvibes

    原创 Lex和Yacc从入门到精通(7)-筛选信息(容错处理)收藏

    新一篇: 应用篇_撤销(Undo)和重做(Redo)的C++自动化实现(1)---交换函数swap功能的讨论 | 旧一篇: Undo(Redo)撤销和重做代码的最后测试文件(相当于文档)

     
    #if 0
     
        在通常的情况下,我们只关心文本中的一部分信息,但是为了编写词法和语法分析程
    序,又不得不将所有的结构信息全部描写出来,例如:我们仅仅关心C++源文档中的类名字
    信息,而不关心类是否有成员变量,是否有成员函数以及是否有其它的一些C++内容。将结
    构信息全部描述出来的做法是费时费力的,通常的情况往往导致项目的不可完成或者延期
    完成。另外,作为程序设计者和代码编写者,都希望将功能局域化而不扩散难度,也非常
    希望编写的代码能够简单的不予理睬还没有理解的内容,专心处理自己关心的内容。本篇
    文档就以着重考虑处理C/C++类名称信息为例,忽略其它的一切没有进行语法描述的C/C++
    信息。这就是Lex和Yacc的错误(error)处理的一个应用:)我非常喜欢:)
     
        下面给出词法和语法分析器的源代码,因为这么简单的程序,看源代码是学习的最好
    方法:)
     
    #endif
     
    ////////////////////////////////////////////////////////////////////////////////
    // 词法扫描器文件:lex.l
    %{
    #include <string>
     
    // 将yylval的值类型由默认的int修改为std::string类型,实际上可以修改为你认为的任
    // 何类型,仅仅只是需要定一个这样YYSTYPE宏即可,特别注意,这个宏定义必须在后面
    // 的标记文件yacc.tab.h之前定义,并且在yacc文件中也要有这个YYSTYPE定义,并且必
    // 须和这里的保持一致。实际上YYSTYPE的定义在生成的标记文件yacc.tab.h中有一个宏
    // 判断,如果用户也就是我们定义了YYSTYPE宏,那么就用我们定义的YYSTYPE,否则就用
    // 默认的YYSTYPE,也就是int类型:)
     
    #define YYSTYPE std::string
    #include "yacc.tab.h"
     
    #define LEX_RETURN(arg) yylval=yytext;return arg
    %}
    d   [0-9]
    l   [a-z]
    u   [A-Z]
    a   {l}|{u}
    %%
    [;{}]                   {LEX_RETURN(yytext[0]);}
    "class"                 {LEX_RETURN(CLASS);}
     
    (_|{a})(_|{a}|{d})*     {LEX_RETURN(IDENTIFIER);}
     
    [ \t\n]                 /* 忽略空白 */
    .                       /* 忽略其它一切没有被处理的文本 */
    %%
    int yywrap()
    {
        return 1;
    }
    ////////////////////////////////////////////////////////////////////////////////
     
     
    ////////////////////////////////////////////////////////////////////////////////
    // 语法分析器文件:yacc.y
    %{
    #include <iostream>
    #define YYSTYPE std::string
    extern int yylex();
    void yyerror(const char*msg);
    %}
    %token CLASS IDENTIFIER
    %%
    program:/* 空 */
           | program class //处理C++ 类
           | program error ';' // 一旦出现错误直接跳到最近的分号处,回复正常的扫描过程
                               // 特别注意这里的标记符号error,它是由yacc自动生成的标记
                               // 和上面的CLASS和IDENTIFIER标记一样都可以直接应用到语法
                               // 描述中
           ;
    class:// 特别注意一下下面的class语法描述又调用了program,这是一种嵌套结构的常见做法
           CLASS IDENTIFIER '{' program '}' ';' {std::cout<<"发现类名:"<<$2<<std::endl;}
         ;
    %%
    void yyerror(const char*msg)
    {
        // 错误处理,仅仅是简单的输出一个错误标记,在具体应用中应当能够分析出这种错
        // 误是否已经被处理了,这里为了说明上面的错误信息过滤没有进行这种识别
        std::cerr<< "发现错误" << std::endl;
    }
    int main()
    {
        yyparse();
        return 0;
    }
    ////////////////////////////////////////////////////////////////////////////////
     
    ////////////////////////////////////////////////////////////////////////////////
    // Makefile文件
    CC=g++
    CFLAGS=
    LEX=flex
    YACC=bison
    YACCFLAGS=-d
    TARGET=lexyacc
     
    $(TARGET):lex.yy.c yacc.tab.h yacc.tab.c
        $(CC) $(CFLAGS) lex.yy.c yacc.tab.c -o $(TARGET)
    lex.yy.c:lex.l
        $(LEX) lex.l
    yacc.tab.c yacc.tab.h:yacc.y
        $(YACC) $(YACCFLAGS) yacc.y
     
    clean:
        rm -f lex.yy.c yacc.tab.h yacc.tab.c
    ////////////////////////////////////////////////////////////////////////////////
     
    // 从上面的代码中可以看出,通过容错处理之后,我们就可以专心于特定的功能代码编写
    // 而不需要考虑其它的信息,这样就可以极大的降低解决问题的难度。在后续的文档中都
    // 会采用这种技巧来实现特定的功能。如果对上面的一些描述还不是很清晰的话,可以参
    // 见我之前已经写出来的系列文档,在本章中值得说明的只有两点:
    // 1:yacc自动生成的error标记的使用
    // 2:改变默认的yylval的int类型为std::string类型
    // 其实我是在尽可能的使用C++库,目的当然是降低编写代码的难度,减少代码,便于说
    // 明问题;)
    //
    // 好了,本篇文档到此就已经说明了本文开始所提出的问题:D,后续的文档正在努力给出
    // 。其实编写Lex和Yacc程序非常简单,只需要注意几个常见错误就可以完成一般的任务
    // 了,在下一篇里面将会讲解常见的错误及其处理方法:)敬请关注:)
     
    // 下面是实例应用
    ////////////////////////////////////////////////////////////////////////////////
    // 测试文件:sample.cpp
    class Point
    {
        int x;
        int y;
        int GetX();
        int GetY();
    };
     
    class Rect
    {
        int x;
        int y;
        int w;
        int h;
        int GetX();
        int GetY();
        int GetW();
        int GetH();
    };
     
    class Wrapper
    {
        class Inner1{};
        class Inner2{
            class InnerInner1{float f;};
            class InnerInner2{};
            std::string name;
        };
        bool sex;
    };
    ////////////////////////////////////////////////////////////////////////////////
     
    ////////////////////////////////////////////////////////////////////////////////
    // 编译并运行过程
    D:\home\blog\lexyacc>make
    flex lex.l
    bison -d yacc.y
    g++ lex.yy.c yacc.tab.c -o lexyacc
     
    D:\home\blog\lexyacc>lexyacc.exe < sample.cpp
    发现错误
    发现类名:Point
    发现错误
    发现类名:Rect
    发现类名:Inner1
    发现错误
    发现类名:InnerInner1
    发现类名:InnerInner2
    发现错误
    发现类名:Inner2
    发现错误
    发现类名:Wrapper
     
    D:\home\blog\lexyacc>
    ////////////////////////////////////////////////////////////////////////////////

    发表于 @ 2007年03月21日 21:28:00|评论(loading...)|编辑

    评论

    #songxin328 发表于2007-08-22 13:23:42  IP: 61.152.161.*
    使用yacc遇到了规约规约冲突,在网上搜了下没有发现解决方法的介绍。
    谁有这方面的资料呢?烦请告之,呵呵,谢谢先~
    #imath 发表于2007-12-19 09:04:14  IP: 222.180.22.*
    老大我引用了你的 这系列文章,嘿嘿
    发表评论  


    当前用户设置只有注册用户才能发表评论。如果你没有登录,请点击登录
    Csdn Blog version 3.1a
    Copyright © pandaxcl