Napravila sam skener i parser koristeci bison++ i flex++ koji treba da vraca string iz ucitane datoteke. Konkretno, radi se o html parseru. Ovo je test primer za vracanje stringa. Problem se pojavljuje prilikom vracanja vrednosti stringa iz skenera u parser. Naime, prilikom ispisa $$ vrednosti u parseru, uvek ce se pojavljivati neki trash. Ima li neko ideju zasto je to tako i kako bi ovaj problem mogao da se resi?
parser.y
Code:
%name Parser
%define LSP_NEEDED
%define MEMBERS \
virtual ~Parser() {} \
private: \
yyFlexLexer lexer;
%define LEX_BODY {return lexer.yylex();}
%define ERROR_BODY {cerr << "error encountered at line: "<<lexer.lineno()<<" last word parsed:"<<lexer.YYText()<<"\n";}
%header{
#include <iostream>
#include <fstream>
#include <FlexLexer.h>
#include <cstdlib>
#include <stdio.h>
#include <string>
#define YYSTYPE char *
using namespace std;
%}
%{
ofstream out;
yyFlexLexer yylval;
%}
%union {
char* str;
}
%token <str> STRING
%start html_start
%%
html_start
: text {
$<str>$=$<str>1;
cout<<" proba2 "<<$<str>1;
}
|{cout<<" proba ";}
;
text
:STRING {$<str>$=$<str>1;}
;
%%
int main(int argc, char ** argv )
{
Parser parser;
ifstream inp;
string myFileName;
myFileName = "mydata.txt";
inp.open(myFileName.c_str(), ifstream::in);
inp.close();
inp.clear(ios::failbit);
out.open("mydata.txt", ofstream::out);
return (parser.yyparse());
out.close();
}
%name Parser
%define LSP_NEEDED
%define MEMBERS \
virtual ~Parser() {} \
private: \
yyFlexLexer lexer;
%define LEX_BODY {return lexer.yylex();}
%define ERROR_BODY {cerr << "error encountered at line: "<<lexer.lineno()<<" last word parsed:"<<lexer.YYText()<<"\n";}
%header{
#include <iostream>
#include <fstream>
#include <FlexLexer.h>
#include <cstdlib>
#include <stdio.h>
#include <string>
#define YYSTYPE char *
using namespace std;
%}
%{
ofstream out;
yyFlexLexer yylval;
%}
%union {
char* str;
}
%token <str> STRING
%start html_start
%%
html_start
: text {
$<str>$=$<str>1;
cout<<" proba2 "<<$<str>1;
}
|{cout<<" proba ";}
;
text
:STRING {$<str>$=$<str>1;}
;
%%
int main(int argc, char ** argv )
{
Parser parser;
ifstream inp;
string myFileName;
myFileName = "mydata.txt";
inp.open(myFileName.c_str(), ifstream::in);
inp.close();
inp.clear(ios::failbit);
out.open("mydata.txt", ofstream::out);
return (parser.yyparse());
out.close();
}
scanner.l
Code:
%option c++
%{
#include<sstream>
#include <iostream>
#include "parser.h"
#include "function.h"
#include <cstdlib>
extern yy_Parser_stype yylval;
%}
text [_a-zA-Z][_a-zA-Z0-9]*
DIGIT [0-9]
%%
{text} { yylval.str= strdup(yytext); return Parser::STRING;}
" "+ {}
<<EOF>> {
yyterminate();
}
%%
int yywrap(void) { return (1); }
%option c++
%{
#include<sstream>
#include <iostream>
#include "parser.h"
#include "function.h"
#include <cstdlib>
extern yy_Parser_stype yylval;
%}
text [_a-zA-Z][_a-zA-Z0-9]*
DIGIT [0-9]
%%
{text} { yylval.str= strdup(yytext); return Parser::STRING;}
" "+ {}
<<EOF>> {
yyterminate();
}
%%
int yywrap(void) { return (1); }
makefile
Code:
EXECUTABLE=parser
CC=g++
LEX=flex++
YACC=bison++
SOURCES=parser.cpp scanner.cpp
OBJECTS=$(SOURCES:.cpp=.o)
.PHONY: clean
default:
$(YACC) -d -hparser.h -o parser.cpp parser.y
$(LEX) -d -oscanner.cpp scanner.l
$(CC) -c $(SOURCES)
$(CC) -o $(EXECUTABLE) $(OBJECTS)
clean:
rm $(EXECUTABLE) $(OBJECTS) *~ -fv
EXECUTABLE=parser
CC=g++
LEX=flex++
YACC=bison++
SOURCES=parser.cpp scanner.cpp
OBJECTS=$(SOURCES:.cpp=.o)
.PHONY: clean
default:
$(YACC) -d -hparser.h -o parser.cpp parser.y
$(LEX) -d -oscanner.cpp scanner.l
$(CC) -c $(SOURCES)
$(CC) -o $(EXECUTABLE) $(OBJECTS)
clean:
rm $(EXECUTABLE) $(OBJECTS) *~ -fv