Flex和Bison GCC编译错误,未找到-lfl的ld:library

Flex和Bison GCC编译错误,未找到-lfl的ld:library,c,gcc,bison,C,Gcc,Bison,在为简单扫描仪编译flex和bison源代码时,我遇到以下错误: $ gcc -o lab5 lab5.tab.c lex.yy.c -lfl ld: library not found for -lfl clang: error: linker command failed with exit code 1 (use -v to see invocation) lex源代码: %{ #include <stdio.h> #include <string.h> #in

在为简单扫描仪编译flex和bison源代码时,我遇到以下错误:

$ gcc -o lab5 lab5.tab.c lex.yy.c -lfl
ld: library not found for -lfl
clang: error: linker command failed with exit code 1 (use -v to see invocation)
lex源代码:

%{

#include <stdio.h>
#include <string.h>
#include "lab5.tab.h"
void showError();
%}

integer (\+?[1-9][0-9]*)
id ([a-zA-Z_][a-zA-Z0-9_]*)

%%

{id} {sscanf(yytext, "%s", yylval.name); return ID;}
{integer} {yylval.number = atoi(yytext); return INT;}
";" return SEMICOLON;
. {showError(); return OTHER;}

%%

void showError() {
    printf("Other input");
}
%{
    #include <stdio.h>
    int yylex();
    int yyerror(char *s);
%}

%token ID INT SEMICOLON OTHER

%type <name> ID
%type <number> INT

%union {
    char name[20];
    int number;
}

%%
prog:
    stmts
;
stmts:
        | stmt SEMICOLON stmts

stmt:
        ID {
                printf("Your entered an id - %s", $1);
        }
        | INT {
                printf("The integer value you entered is - %d", $1);
        }
        | OTHER
;
%%

int yyerror(char *s) {
    printf("Syntax error on line: %s\n", s);
    return 0;
}

int main() {
    yyparse();
    return 0;
}
我正在使用macOS Mojave 10.14.6,包括:

  • 野牛(GNU野牛)2.3
  • flex 2.5.35苹果(flex-31)
  • 通用条款4.2.1

在OS X上,默认的flex安装安装了一个名为
l
的库,而不是
fl
,这使它与原始的“lex”兼容(但与任何其他模糊的现代flex安装不兼容)

因此,您可以使用
-ll
而不是
-lfl
,但不要这样做。您只需要该库,因为您没有告诉flex不需要出现
yywrap
。将以下内容添加到flex文件的开头:

%option noinput nounput noyywrap nodefault
前两个选项通过删除其定义来抑制关于未使用
input
unput
的叮当声/GCC警告。(如果你真的使用了它们,你当然希望它们被定义,但你没有。)

第三个选项,
noyywrap
,告诉flex当扫描器在其输入上遇到文件结束指示时,禁止调用
yywrap
。您可以添加
yywrap
的定义,无条件地确认文件的结尾,但这是毫无意义的;如果您不打算使用扫描仪的该功能,那么在调用dummy
yywrap
时进行编译是没有意义的


第四个选项告诉flex,如果存在一些规则都不匹配的输入模式,就要抱怨。默认情况下,flex扫描仪通过在标准输出(或
yyout
指向的任何内容)上打印不匹配字符来响应不匹配的输入,而不进行任何其他错误处理。这很少是您想要的,因此最好知道有一些输入错误将被默默忽略,以便您可以修复它。不幸的是,flex没有告诉您是什么模式触发了错误,因此我将告诉您答案:
与换行符不匹配,并且flex文件中的其他内容也不匹配。你应该解决这个问题。(
|\n
是“其他任何东西”的模式。)

在OS X上,默认的flex安装安装了一个名为
l
的库,而不是
fl
,这使得它与原始的“lex”兼容(但与任何其他模糊的现代flex安装不兼容)

因此,您可以使用
-ll
而不是
-lfl
,但不要这样做。您只需要该库,因为您没有告诉flex不需要出现
yywrap
。将以下内容添加到flex文件的开头:

%option noinput nounput noyywrap nodefault
前两个选项通过删除其定义来抑制关于未使用
input
unput
的叮当声/GCC警告。(如果你真的使用了它们,你当然希望它们被定义,但你没有。)

第三个选项,
noyywrap
,告诉flex当扫描器在其输入上遇到文件结束指示时,禁止调用
yywrap
。您可以添加
yywrap
的定义,无条件地确认文件的结尾,但这是毫无意义的;如果您不打算使用扫描仪的该功能,那么在调用dummy
yywrap
时进行编译是没有意义的


第四个选项告诉flex,如果存在一些规则都不匹配的输入模式,就要抱怨。默认情况下,flex扫描仪通过在标准输出(或
yyout
指向的任何内容)上打印不匹配字符来响应不匹配的输入,而不进行任何其他错误处理。这很少是您想要的,因此最好知道有一些输入错误将被默默忽略,以便您可以修复它。不幸的是,flex没有告诉您是什么模式触发了错误,因此我将告诉您答案:
与换行符不匹配,并且flex文件中的其他内容也不匹配。你应该解决这个问题。(
|\n
是“其他任何内容”的模式)。

-ll
符合POSIX,而
-lfl
则不符合。@jl2210:确实如此。大多数flex安装还添加了
libl
,以保持Posix兼容性。但本世纪的普遍做法是使用
-lfl
。顺便说一下:C是一种语言,flex是一种扫描生成器
c99
是用于运行C编译器的命令,
lex
是用于运行扫描仪生成器的命令(至少在Posix系统上)。我没有还原你的编辑,但它有点刺痛;我试图在使用代码格式时保持一致。这一点很好。我已经删除了我所做的所有代码格式设置,因为它实际上没有太大改进。
-ll
符合POSIX,而
-lfl
则不符合。@jl2210:这是真的。大多数flex安装还添加了
libl
,以保持Posix兼容性。但本世纪的普遍做法是使用
-lfl
。顺便说一下:C是一种语言,flex是一种扫描生成器
c99
是用于运行C编译器的命令,
lex
是用于运行扫描仪生成器的命令(至少在Posix系统上)。我没有还原你的编辑,但它有点刺痛;我试图在使用代码格式时保持一致。这一点很好。我已经删除了我所做的所有代码格式设置,因为它实际上没有太大的改进。