0

例如,我在 .ypp 中有这个声明:

%{
#include <iostream>
#include <stdlib.h>
#include "structs.h"
#include "func.h"
#define YYSTYPE Types
%}
%union Types{
   int Integer;
   bool Boolean;
   Expression Exp;
 };

在“structs.h”中我有:

typedef union{
string str;
int integer;
bool boolean;
} Value;

struct Expression {
int lineNum;
Value val;
};

在“func.h”中我有这个函数:

int binop(Types& a, Types& b); //assume all file needed included

我可以在 .ypp 中传递 $$ arg:

Exp : Exp Add Exp {$$.integer = binop($1, $2);}
4

1 回答 1

2

您当然可以通过引用传递语义值,但您不能假设该引用在执行语义操作之后仍然有效。所以不要保持对语义值的持久引用。

语义值存储在解析器堆栈中,并且解析器堆栈槽在解析器方便时被重用(因为它实际上是一个堆栈)。特别是,$1...$nslots 在语义动作执行后立即弹出,while$$是一个临时的,在$1...$n弹出后被推送(复制)到堆栈上。

即使值没有立即弹出——就像中间规则语义操作的情况——解析器堆栈也可能被重新分配(从而使所有引用无效)以适应推送。

于 2019-12-18T17:21:51.400 回答