compiling flex and bison into cpp

杀马特。学长 韩版系。学妹 提交于 2019-12-10 21:24:42

问题


Usually, when we compile .l and .y files, we get .tab.h,.tab.c and .yy.c files. However, I need to use these in a C++ environment with types that are only available in C++. How do you modify your code so as to do this?


回答1:


You can compile the generated files using your trustworthy C++ compiler, so you don't have to rewrite the whole thing.

If you want to go "full c++", keep reading.

For Flex, you need to specifiy %option c++ in the file. You can also change the generated C++ lexer name using --yyclass=NAME command line argument.

For Bison, just follow these instructions (excerpt taken from Bison manual)

if you need to put  C++  code  in  the
input  file, you can end his name by a C++-like extension (.ypp or .y++), then bison will follow your exten-
sion to name the output file (.cpp or .c++).  For instance, a grammar description file named parse.yxx would
produce the generated parser in a file named parse.tab.cxx, instead of yacc y.tab.c or old Bison version's
parse.tab.c.

P.S: Be aware that c++ and reentrant options are mutually exclusive in Flex.




回答2:


You can specify output filenames with command-line flags, so you don't need to modify your code at all to produce .cc files, which will save you some complication with makefiles or equivalent.

As long as your actions and other code blocks are valid C++ code and you don't include non-POD types in the semantic union directly (pointers are fine; smart pointers, not), you shouldn't need to modify anything.

You could also use the C++ templates in flex and bison, but I've generally found it easier to stick with the C templates, which will compile just fine with C++.




回答3:


I'd try this tutorial for Flex/Bison in C++: http://www.jonathanbeard.io/tutorials/FlexBisonC++

The code repository is up to date and compatible with the latest C++ compilers: https://github.com/jonathan-beard/simple_wc_example

Specifically I'd take a look at the examples

void 
MC::MC_Driver::add_word( const std::string &word )
{
   words++; 
   chars += word.length();
   for(const char &c : word ){
      if( islower( c ) )
      { 
         lowercase++; 
      }
      else if ( isupper( c ) ) 
      { 
         uppercase++; 
      }
   }
}

where a string (C++ type) is passed from the parser (.yy file) here:

item
  : UPPER   { driver.add_upper(); }
  | LOWER   { driver.add_lower(); }
  | WORD    { driver.add_word( $1 ); }
  | NEWLINE { driver.add_newline(); }
  | CHAR    { driver.add_char(); }
  ;

Basically as long as the C++ binary knows how to handle the object then everything will work nicely. To figure out why this works, I'd definitely check out the GitHub repository and play with the code a bit.

Hope this helps. -J



来源:https://stackoverflow.com/questions/26619079/compiling-flex-and-bison-into-cpp

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!