Windows下的yacc lex工具(Z+源码)

本文详细介绍了如何在Windows环境下使用ParserGenerator工具生成Yacc与Lex代码,并通过Visual C++编译器进行编译的过程。包括独立的Yacc文件、Lex文件以及二者结合的文件编译实例。

本测试的源码顺利编译通过,有需要的同仁可以从这里下载:

http://download.csdn.net/source/1151308

或者在csdn资源里搜widnows yacc lex 

 

from: http://blog.csdn.net/JsuFcz/archive/2008/11/18/3331107.aspx

 

  2009-03-28 12:47:22

 

只所以推荐它是因为它生成的c文件可以在vc++下通过编译。
     下载地址 http://www.bumblebeesoftware.com/downloads.htm
下载之后,解压缩,然后安装。打开集成开发环境,点项目Project菜单,在下拉菜单中选LibBuilder,弹出LibBuilder对话框选择属性按钮
弹出compiler properties 对话框,


1.设置 parser generator生成库
Name 选择Visual C++ (32-bit)
Directory :msvc32
options:
依次为
vc++版本(Versoin 7(.net))。
是否支持unicode码。
是否把w_char_t作为内建类型。
下边是VC的各种目录:
依次为
Compiler Bin Directory (C:/PROGRAM FILES/MICROSOFT VISUAL STUDIO .NET 2003/VC7/BIN)
Compiler Bin Directory(C:/PROGRAM FILES/MICROSOFT VISUAL STUDIO .NET 2003/COMMON7/IDE)
Compiler Include Directory(C:/PROGRAM FILES/MICROSOFT VISUAL STUDIO .NET 2003/VC7/INCLUDE)
Compiler Include Directory(C:/PROGRAM FILES/MICROSOFT VISUAL STUDIO .NET 2003/VC7/PLATFORMSDK/INCLUDE)
Compiler Library Directory(C:/PROGRAM FILES/MICROSOFT VISUAL STUDIO .NET 2003/VC7/LIB)
Compiler Library Directory(C:/PROGRAM FILES/MICROSOFT VISUAL STUDIO .NET 2003/VC7/PLATFORMSDK/LIB)
注意:括号里边的是我自己编译器安装目录,也许你的和我的不一样,需要做相应的调整。
所有的这些设置完成之后点ok。返回LibBuilder。点Build就可以编译vc++使用的lex与yacc的lib库。生成库文件在软件安装目录下的D:/Parser Generator 2/Cpp/Lib/msvc32目录下。

Library(DEBUG)

Run-time Library

Description

yld.lib

Debug Single-Threaded

单线程静态链接库(DEBUG版本)

ylmtd.lib

Debug Multithreaded

多线程静态链接库(DEBUG版本)

ylmtrd.lib

Debug Multithreaded DLL

多线程静态链接库当run time library 使用动态库(DEBUG版本)

ylmtrid.lib

Debug Multithreaded DLL

多线程动态链接库当run time library 使用动态库(DEBUG版本)

Library(RELEASE)

Run-time Library

Description

yl.lib

Single-Threaded

单线程静态链接库(RELEASE版本)

ylmt.lib

Multithreaded

多线程静态链接库(RELEASE版本)

ylmtr.lib

Multithreaded DLL

多线程静态链接库当run time library 使用动态库(RELEASE版本)

ylmtri.lib

Multithreaded DLL

多线程动态链接库当run time library 使用动态库(RELEASE版本)

2.设置编译VS
然后我们我们在vc++环境设置中增加包含文件目录D:/Parser Generator 2/Cpp/Include
lib库目录D:/Parser Generator 2/Cpp/Lib/msvc32
具体设置
打开VC++.net集成开发环境。
点工具菜单
下拉菜单中点选项菜单。
弹出框中点左边列表框中的projects,然后点击vc++目录
在显示以下内容目录标签下的列表框中“选包含目录”进行设置,选“库文件”进行设置。
具体设置就是点击列表框下边五个按钮中的第二个按钮,就加入一行,当选择“包含目录”的时候填入D:/Parser Generator 2/Cpp/Include,当选择“库文件”的时候填入D:/Parser Generator 2/Cpp/Lib/msvc32,也可以点右边的浏览按钮进行选择。

3.编译PG
这样设置之后我们就可以用vc++编译用Parser Generator 2生成的c文件。具体为
打开Parser Generator 2集成开发环境。
点击Project菜单,点击下拉菜单中的ParseWizard菜单,一路下去建立一个工程。然后点击project菜单下的的Rebuild All。在项目文件夹下就生成了相应c文件与h文件。
用VC++建立一个空控制台工程,然后把用用Parser Generator 2生成的c文件加入工程中。最后引入响应的库文件,就是我们在D:/Parser Generator 2/Cpp/Lib/msvc32目录下生成的lex与yacc库文件。接着编译,如果成功,那么万事大吉。

 

 


关于yacc lex 和在下面链接的文章里已经有所介绍了
/html/linuxshijie/20070909/80.html
链接中的文章还介绍了在linux下如何使用yacc和lex工具,下面主要是介绍yacc和lex在windows下的用法。


以下内容属作者为xiaolin,请尊重作者的辛勤劳动,请勿转载。

yacc和lex在windows已经移植成功,其中常用的一个工具就是Parser Generator。这个工具使用yacc和lex能够生成Visual C++,Borland C++,Other C/C++以及相关Java代码。下面介绍一下这个工具是如何生成代码并使用Visual C++编译的。
注:关于Parser Generator的使用和配置,其实在Parser Generator Help中已经有很详细的介绍,感兴趣的朋友可以去那里查到更多有用的信息。

首先要去http://www.bumblebeesoftware.com/downloads.htm下载Parser Generator。
安装完毕后,我们可以在它的安装目录下找到一些例子以及编译程序所需的库文件和源文件,这些文件在编译是很重要。

注意:在VS连接的时候会莫名奇妙出现几个链接错,很有可能是lib没有导入进去,这个时候可以在源码里这样设置

#pragma comment(lib,"yl.lib");

单独yacc文件的编译。
以下是一个单独的yacc文件,实现一个简单的计算器功能。
%{
/************************************************************
www.linmu100.com
************************************************************/
#include <ctype.h>
#include <stdio.h>
#define YYSTYPE double /* double type for YACC stack */
%}

%token NUMBER

%%
lines    : lines expr '/n'            { printf("%g/n", $2); }
        | lines '/n'
        | /* e */
        | error '/n'                { yyerror("reenter last line:"); yyerrok(); }
        ;

expr    : expr '+' term                { $$ = $1 + $3; }
        | expr '-' term                { $$ = $1 - $3; }
        | term
        ;

term    : term '*' factor            { $$ = $1 * $3; }
        | term '/' factor            { $$ = $1 / $3; }
        | factor
        ;

factor    : '(' expr ')'                { $$ = $2; }
        | '(' expr error            { $$ = $2; yyerror("missing ')'"); yyerrok(); }
        | '-' factor                { $$ = -$2; }
        | NUMBER
        ;

%%
int main(void)
{
    return yyparse();
}

int yylex(void)
{
    int c;
    while ((c = getchar()) == ' ');
    if (c == '.' || isdigit(c)) {
        ungetc(c, stdin);
        scanf("%lf", &yylval);
        return NUMBER;
    }
    return c;
}

我们用Parser Generator的Project --> Parser Wizard创建一个工程,如下图所示,注意红圈部分的设置:


然后设置文件,模板:


其余按默认完成即可:


这时,我们可以看到
Parser Generator帮我们自动生成了一个myparser.y文件,语法规则就可以在这里加了。


现在我们把开头展示的yacc源码完全覆盖myparser.y文件,然后编译,成功后会生成三个文件:myparser.c,myparser.h,myparser.v
好,现在我们要做的就是用vc来编译myparser.c,myparser.h这两个文件了。

打开Microsoft Visual C++ 6.0,新建一个工程。

然后将
Parser Generator生成的两个文件myparser.c,myparser.h导入工程。(这里就不多说了^-^)
现在要设置环境变量了,首先要导入Parser Generator的库文件和源文件。在工具->选项里要设置这些环境变量。




设置完这些文件后,还要在工程->设置里添加yl.lib库:


好,一切设置完毕,开始编译,编译通过后,就会生成yacc_vc.exe文件。
假设有文件demo.txt,此文件和yacc_vc.exe在同一个目录,其内容如下:
1+3*5
3*4-23
7- 9 *30 - 999
此目录的命令行下运行如下命令:yacc_vc.exe <demo.txt,即可得到计算结果:


单独lex文件的编译。
以下是一个单独的lex文件,实现一个简单的计算单词个数功能。
%{
/************************************************************
www.linmu100.com
************************************************************/
int wc = 0;        /* word count */
%}

%%
[a-zA-Z]+    { wc++; }
/n|.        { /* gobble up */ }

%%

/*#pragma comment(lib,"yl.lib")   //有时候在setting里设置lib会出现连接错误,这个时候可以显示连接*/
int main(void)
{
    int n = yylex();
    return n;
}

int yywrap(void)
{
    printf("word count: %d/n", wc);
    return 1;
}

我们用
Parser Generator新建一个工程:



下一步默认完成即可。这时,Parser Generator帮我们自动生成了一个mylexer.l文件,词法规则可以在这里加。
同样的,我们用上面展示的lex文件内容完全覆盖mylexer.l文件,编译后同样生成三个文件,然后用VC编译其中的mylex.c,mylex.h这两个文件。
VC的设置方法和上面编译单独yacc文件时的步骤完全一样,最终会生成一个可以计算文件单词数目的.exe文件。

yacc 和 lex整合文件的编译。
以下分别是yacc文件和lex文件的内容,这两个文件共同实现了自定义的一个简单语法规则。
yacc文件内容:
%{
/*
www.linmu100.com
*/
#include <stdio.h>
#include <string.h>
void yyerror(const char *str)
{
    fprintf(stderr,"error: %s/n",str);
}
int yywrap()
{
    return 1;
}
main()
{
    yyparse();
}
char *heater="xl's test";
%}

%token TOKHEATER TOKHEAT TOKTARGET TOKTEMPERATURE
%union
{
    int number;
    char *string;
}

%token <number> STATE
%token <number> NUMBER
%token <string> WORD
%%

commands:
    | commands command
    ;
command:
    heat_switch | target_set | heater_select
    ;
heat_switch:
    TOKHEAT STATE
    {
        if($2)
            printf("/tHeater '%s' turned on/n", heater);
        else
            printf("/tHeat '%s' turned off/n", heater);
    }
    ;
target_set:
    TOKTARGET TOKTEMPERATURE NUMBER
    {
        printf("/tHeater '%s' temperature set to %d/n",heater, $3);
    }
    ;
heater_select:
    TOKHEATER WORD
    {
        printf("/tSelected heater '%s'/n",$2);
        heater=$2;
    }
    ;
lex文件内容:
%{
/*
www.linmu100.com
*/
#include <stdio.h>
#include <string.h>
#include "myparser.h"                  //注意,这里的头文件要和
Parser Generator生成的头文件名一样。
extern char *yytext;
%}
%%
[0-9]+                  {yylval.number=atoi(yytext); return NUMBER;}
heater            return TOKHEATER;
heat                    return TOKHEAT;
on|off                  {yylval.number=!strcmp(yytext,"on"); return STATE;}
target                  return TOKTARGET;
temperature             return TOKTEMPERATURE;
[a-z0-9]+        {yylval.string=strdup(yytext);return WORD;}
/n                      /* ignore end of line */;
[ /t]+                  /* ignore whitespace */;
%%

现在用Parser Generator创建新的工程:




其余的步骤和上面编译yacc时的步骤相同,最终可以生成both_y_l.exe文件,放一个demo.txt和both_y_l.exe在同一个目录下,demo.txt内容如下:
heat on
target temperature 99
heater asdfsieiwef99adsf
然后在此目录的命令行下执行both_y_l.exe <demo.txt得到:


以上即为Parser Generator的使用以及如何用VC编译

/
/*-----Lex & Yacc ----www.linmu100.com ----*/
/
/*-----linux工具,Lex & Yacc,windows下操作----*/
/
/*-----linux配置,UNIX,开源软件,linux技术,makefile----*/
/
/*----------------------@xiaolin--------------------*/
/

评论 2
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值