aocpp/lib/include/aocpp/Parsing.hpp
2023-04-08 16:54:22 -07:00

51 lines
1.4 KiB
C++

#ifndef AOCPP_PARSING_HPP_
#define AOCPP_PARSING_HPP_
#include <string>
#include <iostream>
#include <iterator>
#include <vector>
#include <boost/spirit/home/qi.hpp>
namespace aocpp {
auto SplitOn(std::string const& stuff, std::string const& sep) -> std::vector<std::string>;
/// Parse the complete input stream according to the rules defined in 'Grammar'.
/// Throws: std::runtime_error on failed parse
template <typename G>
auto ParseGrammar(G const& grammar, std::istream & in) -> typename G::start_type::attr_type
{
namespace qi = boost::spirit::qi;
auto result = typename G::start_type::attr_type {};
auto const content = std::string{std::istreambuf_iterator{in}, {}};
auto b = content.begin(); // updated on successful parse
auto const e = content.end();
if (!qi::parse(b, e, grammar, result) || b != e) {
throw std::runtime_error{"Bad input file: " + content};
}
return result;
}
template <typename G>
auto ParseGrammar_(G const& grammar, std::istream & in) -> typename G::start_type::attr_type
{
namespace qi = boost::spirit::qi;
auto result = typename G::start_type::attr_type {};
auto const content = std::string{std::istreambuf_iterator{in}, {}};
auto b = content.begin(); // updated on successful parse
auto const e = content.end();
if (!qi::phrase_parse(b, e, grammar, qi::ascii::space, result) || b != e) {
throw std::runtime_error{"Bad input file: " + content};
}
return result;
}
}
#endif