Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/wcf/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Bison 从Flex输出中删除默认YY_DECL_Bison_Flex Lexer - Fatal编程技术网

Bison 从Flex输出中删除默认YY_DECL

Bison 从Flex输出中删除默认YY_DECL,bison,flex-lexer,Bison,Flex Lexer,在手动设置编译器读取头文件的顺序时,我能够避开这个问题。在这种情况下,我可以用正确的定义欺骗默认的“pearl”,但当我无法控制头的包含顺序时,这。。。工程表面的天才: /* Default declaration of generated scanner - a define so the user can * easily add parameters. */ #ifndef YY_DECL #define YY_DECL_IS_OURS 1 /* %if-c-only Standard

在手动设置编译器读取头文件的顺序时,我能够避开这个问题。在这种情况下,我可以用正确的定义欺骗默认的“pearl”,但当我无法控制头的包含顺序时,这。。。工程表面的天才:

/* Default declaration of generated scanner - a define so the user can
 * easily add parameters.
 */
#ifndef YY_DECL
#define YY_DECL_IS_OURS 1
/* %if-c-only Standard (non-C++) definition */

extern int yylex \
               (YYSTYPE * yylval_param,YYLTYPE * yylloc_param ,yyscan_t yyscanner);

#define YY_DECL int yylex \
               (YYSTYPE * yylval_param, YYLTYPE * yylloc_param , yyscan_t yyscanner)
/* %endif */
/* %if-c++-only C++ definition */
/* %endif */
#endif /* !YY_DECL */
这是在头文件中定义的,但是我对
YY_DECL
的定义被复制到
*.c
文件中

文件说:

(如果您的环境支持函数原型,那么它将是“int-yylex(void)”。可以通过定义“YY_-DECL”宏来更改此定义。例如,您可以使用:

将扫描例程命名为lexscan,返回一个浮点,并将两个浮点作为参数。请注意,如果使用K&R样式/非原型函数声明为扫描例程提供参数,则必须使用分号(`;')终止定义

是的,对,就是我错过的!如果我不能使用在七十年代消亡的非标准C语法,我将如何生活?然而,文档公然隐瞒了如果您声明
YY_DECL
会发生什么:实际上它会被忽略,除非您在编译Flex生成的任何代码之前设法向编译器伪造不同的头


我现在只需要编写一个
sed
调用来修补Flex的输出。请告诉我,实际上可以在没有这种“插装”的情况下修复它。

如果您想更改原型以添加包含额外状态的参数,通常使用Flex的功能,
yytextra
更容易。这避免了YY_DECL的刺激

另一方面,如果您想要更改生成的lexer的名称(例如,因为您想要导出一个名为
yylex
)的包装器),那么一种粗糙但有效的技术就是

#define yylex my_name
在开场白和

#undef yylex
在结语中。(显然,这些文件不应该放在头文件中。)


我同意
YY_DECL
宏远不是配置
yylex
原型的理想方式。我的抱怨一直是,一旦你有了
yylex
的参数(就像你对可重入的lexer所做的那样),你就需要得到正确的名称,并且正确的名称没有文档记录,因此可能会发生更改,导致将来在等待时出现不兼容。

可能没有解决方案能让你满意。我同意
YY_DECL
不是配置
yylex
原型的理想方式,尤其是因为一旦你有了
yylex
的参数(就像你使用可重入的lexer和解析器一样),你就需要正确地使用它们的名称,并且正确的名称没有被记录下来。但是,了解为什么要更改原型会很有用。要添加额外的状态,通常更易于使用。如果您只是想更改名称,那么
#define yylex my_name
虽然粗糙但有效。我将尝试
yytextra
-不知道这一点。我今天回来报到。是的,我的目标是添加一个额外的参数,因为解析器是可重入的,所以我需要传递状态?IMHO,这是可重入解析(以及其他原因)的最佳解决方案。为此,我经常使用
yytextra
,尽管有时在yylex顶部分配解析状态并在发送结束标记后将其删除比较方便。@rici是的,我使用的是推式解析器。@rici是的,它与yytextra一起工作。如果你想的话,你可以把这个贴出来作为答案,我会接受的。
#undef yylex