Boost C++ Libraries Home Libraries People FAQ More


Getting started with Boost.Metaparse

1. Introduction
2. The text to parse
3. Creating a simple parser
4. Parsing simple expressions
5. Parsing longer expressions
6. Adding support for other operators
7. Dealing with precedence
8. Dealing with associativity
9. Dealing with unary operators
10. Dealing with parens
11. Dealing with invalid input
12. Summary
Copy-paste friendly code examples
Definitions before each section

This tutorial shows you how to build a parser for a small calculator language from the ground up. The goal is not to have a complete calculator, but to show you the most common situations one can face while building a parser using Metaparse. This tutorial assumes, that you have some template metaprogramming experience.

While you are using Metaparse, you will be writing parsers turning an input text into a type. These types can later be processed by further template metaprograms. While you are working on your parsers, you'll probably want to look at the result of parsing a test input. This tutorial assumes that you can use Metashell. Since the online demo makes the Boost headers available, you can use that in the tutorial as well.

If you install Metashell on your computer, make sure that you have the Boost libraries and the getting_started example of Metaparse on the include path. For example, you can start Metashell with the following arguments:

$ metashell -I$BOOST_ROOT -I$BOOST_ROOT/libs/metaparse/example/getting_started

$BOOST_ROOT refers to the the boost root directory (where you have checked out the Boost source code).

This tutorial is long and therefore you might want to make shorter or longer breaks while reading it. To make it easy for you to stop at a certain point and continue later (or to start in the middle if you are already familiar with the basics) Metaparse has a getting_started directory in the examples. This contains the definitions for each section of this tutorial.

If you're about to start (or continue) this guide from section 5.2.1, you can include 5_2_1.hpp. This will define everything you need to start with that section.

[Note] Note

You have access to these headers in the online Metashell demo as well. For example you can include the <boost/metaparase/getting_started/5_2_1.hpp> header to start from section 5.2.1.

If you have no access to Metashell or you prefer using your regular C++ development environment while processing this tutorial, this is also possible.

The tutorial (and usually experimenting with Metaparse) requires that you evaluate different template metaprogramming expressions and check their result, which is a type. Thus, to try the examples of this tutorial you need a way to be able to display the result of evaluating a template metaprogram. This section shows you two options.

You can either use boost::mpl::print or mpllibs::metamonad::fail_with_type to enforce a warning or an error message containing the result of a metaprogram evaluation. For example to see what BOOST_METAPARSE_STRING("11 + 2") refers to, you can create a test.cpp with the following content:

#include <boost/metaparse/string.hpp>
#include <boost/mpl/print.hpp>

boost::mpl::print<BOOST_METAPARSE_STRING("11 + 2")> x;

If you try to compile it, the compiler will display warnings containing the type the expression BOOST_METAPARSE_STRING("11 + 2") constructs. To use this technique for this tutorial, you need to add all the includes and definitions the tutorial suggests typing in the shell to your test.cpp file. When the shell suggests to try to call some metafunction (or you'd like to try something out), you need to replace the template argument of boost::mpl::print with the expression in question and recompile the code.

You can also display the result of metaprograms at runtime. You can use the Boost.TypeIndex library to do this. For example to see what BOOST_METAPARSE_STRING("11 + 2") refers to, you can create a test.cpp with the following content:

#include <boost/metaparse/string.hpp>
#include <boost/type_index.hpp>
#include <iostream>

int main()
    << boost::typeindex::type_id_with_cvr<BOOST_METAPARSE_STRING("11 + 2")>()
    << std::endl;

If you compile and run this code, it will display the type on the standard output.