%{
#define FUNCT 300
#define IDENTIFIER 301
#define ASSGN 302
#define INTEGER 303
#define PRINT 304
#define TEXT 305
#define INPUT 306
#define CONTINUE 307
#define RETURN 308
#define IF 309
#define THEN 310
#define ENDIF 311
#define ELSE 312
#define WHILE 313
#define DO 314
#define ENDDO 315
#define END 316
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
#define MAX_SYM 200
int found;
void initialize();
void create(char *lexeme, int scope, char type, char usage);
int readsymtab(char *lexeme, int scope, char usage);
%}
%%
[t ]+ {}
= {int found = readsymtab(yytext,0,'L');
if(found == -1)
{
create(yytext,0,'S','L');
};
return(ASSGN) ;}
print {int found = readsymtab(yytext,0,'L'); //line 39
if(found == -1)
{
create(yytext,0,'S','L');
};
return(PRINT) ;}
input {int found = readsymtab(yytext,0,'L');
if(found == -1)
{
create(yytext,0,'S','L');
};
return(INPUT) ;}
continue {int found = readsymtab(yytext,0,'L');
if(found == -1)
{
create(yytext,0,'S','L');
};
return(CONTINUE) ;}
return {int found = readsymtab(yytext,0,'L');
if(found == -1)
{
create(yytext,0,'S','L');
};
return(RETURN) ;}
if {int found = readsymtab(yytext,0,'L');
if(found == -1)
{
create(yytext,0,'S','L');
};
return(IF) ;}
then {int found = readsymtab(yytext,0,'L');
if(found == -1)
{
create(yytext,0,'S','L');
};
return(THEN) ;}
endif {int found = readsymtab(yytext,0,'L');
if(found == -1)
{
create(yytext,0,'S','L');
};
return(ENDIF) ;}
else {int found = readsymtab(yytext,0,'L');
if(found == -1)
{
create(yytext,0,'S','L');
};
return(ELSE) ;}
while {int found = readsymtab(yytext,0,'L');
if(found == -1)
{
create(yytext,0,'S','L');
};
return(WHILE) ;}
do {int found = readsymtab(yytext,0,'L');
if(found == -1)
{
create(yytext,0,'S','L');
};
return(DO) ;}
enddo {int found = readsymtab(yytext,0,'L');
if(found == -1)
{
create(yytext,0,'S','L');
};
return(ENDDO) ;}
end {int found = readsymtab(yytext,0,'L');
if(found == -1)
{
create(yytext,0,'S','L');
};
return(END);
exit(0); ;}
funct {int found = readsymtab(yytext,0,'L');
if(found == -1)
{
create(yytext,0,'S','L');
};
return(FUNCT) ;}
[0-9]+ {int found = readsymtab(yytext,0,'L');
if(found == -1)
{
create(yytext,0,'I','L');
};
return(FUNCT) ;}
[a-zA-Z]+ {int found = readsymtab(yytext,0,'I');
if(found == -1)
{
create(yytext,0,'S','I');
};
return(IDENTIFIER) ;}
"[^"n]+|[\n]+" {int found = readsymtab(yytext,0,'L'); //line130
if(found == -1)
{
create(yytext,0,'S','L');
};
return(TEXT) ;}
. {return(yytext[0]) ;}
%%
//new variable declaration
int num;
int scope;
struct symbtab
{
char Lexeme [18];
int Scope;
char Type;
char Usage;
int Reference;
};
struct symbtab arr_symtab[200]; //data structure in which the symbol table entries are stored
void print_fn() //function which actually prints the symbol tabel in columnar form
{
int rows;
printf("Row No Lexeme Scope Type Usage Referencen");
for (rows=0; rows<=num; rows++){
printf("%6d %-16s %-7d %-7c %-7c %-7d n",rows, arr_symtab[rows].Lexeme,arr_symtab[rows].Scope,arr_symtab[rows].Type,arr_symtab[rows].Usage,arr_symtab[rows].Reference);
}
}
void initialize() //function which enteres the initial value into the symbol table
{
num = -1;
int scope = 0;
char lexeme[18]= "FRED";
char type = 'I';
char usage = 'L';
create(lexeme,scope,type,usage);
}
void create(char *lexeme, int scope, char type, char usage) //function which creates a new entry in the symbol table
{
int reference;
if(type=='I' && usage =='L')
reference = atoi(lexeme);
else
reference = -1;
num = num+1;
strcpy(arr_symtab[num].Lexeme, lexeme);
arr_symtab[num].Scope = scope;
arr_symtab[num].Type = type;
arr_symtab[num].Usage = usage;
arr_symtab[num].Reference = reference;
}
int readsymtab(char *lexeme, int scope, char usage) //function which checks if the entry is already in the table or not and the takes the required action
{
for(int i=num; i>=0; i--){
int comp = strcmp(arr_symtab[i].Lexeme, lexeme);
if(comp==0 && arr_symtab[i].Scope==scope && arr_symtab[i].Usage==usage)
{
return i;
}
else
{
return -1;
}
}
}
int main()
{
//other lines
printf("n COURSE: CSCI50200 NAME: Aryan Banyal NN: 01 Assignment #: 04 n");
initialize();
yylex();
print_fn();
printf("End of test.n");
return 0;
}
int yywrap ()
{
return 1;
}
下面是打印";雅利安banyal";
COURSE: CSCI50200 NAME: Aryan Banyal NN: 01 Assignment #: 04
--(end of buffer or a NUL)
--accepting rule at line 39 ("print")
Row No Lexeme Scope Type Usage Reference
0 FRED 0 I L 0
1 print 0 S L -1
End of test.
正如你所看到的,它甚至不会去";雅利安banyal";part只是做打印的事情然后退出。。。下面是"0"的输出;雅利安banyal";
COURSE: CSCI50200 NAME: Aryan Banyal NN: 01 Assignment #: 04
--(end of buffer or a NUL)
--accepting rule at line 130 (""aryan banyal")
Row No Lexeme Scope Type Usage Reference
0 FRED 0 I L 0
1 "aryan banyal 0 S L -1
End of test.
第一排应该是雅利安榕树,但有一个";之前因为某种原因。
您(至少(有三个(有些(不相关的问题。
使用词法扫描仪
您的代码在读取单个令牌后停止,因为您只调用yylex()
一次(并忽略它返回的内容(。yylex()
每次调用时都返回一个令牌;如果要扫描整个文件,则需要循环调用它。当遇到输入结束时,它将返回0。
了解模式
图案CCD_ 3在中间具有CCD_;该运算符匹配它周围的任何一个模式。因此您匹配的是"[^"n]+
或[\n]+"
。第一个匹配一个双引号,后跟任意数量的字符(但至少一个(,不能是引号或新行。因此,它与"aryan banyal
匹配,不包含结束引号,但包含开放引号。备选方案的后半部分将匹配任意数量的字符(同样,至少一个(,所有这些字符要么是反斜杠,要么是字母n
,然后是单双引号。
(我不理解这种模式背后的想法,几乎可以肯定这不是你想要的。如果你在"aryan banyal
匹配后再次调用yylex
,那么结束引号就不会匹配,因为它将是紧接着的下一个字符,并且该模式坚持要求它前面至少有一个反斜杠或n
。(。(也许你想让它成为一条新线路,但也没有。(
我想你可能想匹配整个引号字符串,然后只保留引号之间的部分。如果你写对了模式,它就会匹配,然后你需要去掉双引号。我将把写正确的模式作为练习。您可能想阅读Flex手册中对Flex模式的简短描述;你可能在课堂笔记中也有一些信息。
只选择比赛的一部分
删除标记开头的引号很容易。所需要的只是向yytext
添加一个。要去掉末尾的一个,需要用