Changed to use SemanticValues instead of SemanticStack.

This commit is contained in:
yhirose 2015-02-08 23:02:24 -05:00
parent feebade357
commit 0efe8110e4

153
peglib.h
View File

@ -325,7 +325,7 @@ template <typename T>
struct SemanticActions; struct SemanticActions;
template <typename T> template <typename T>
struct SemanticStack; struct SemanticValues;
/* /*
* Match * Match
@ -373,7 +373,7 @@ public:
Sequence(std::vector<std::shared_ptr<Rule>>&& rules) : rules_(std::move(rules)) {} Sequence(std::vector<std::shared_ptr<Rule>>&& rules) : rules_(std::move(rules)) {}
template <typename T> template <typename T>
Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const; Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const;
private: private:
std::vector<std::shared_ptr<Rule>> rules_; std::vector<std::shared_ptr<Rule>> rules_;
@ -402,7 +402,7 @@ public:
PrioritizedChoice(std::vector<std::shared_ptr<Rule>>&& rules) : rules_(std::move(rules)) {} PrioritizedChoice(std::vector<std::shared_ptr<Rule>>&& rules) : rules_(std::move(rules)) {}
template <typename T> template <typename T>
Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const; Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const;
private: private:
std::vector<std::shared_ptr<Rule>> rules_; std::vector<std::shared_ptr<Rule>> rules_;
@ -414,7 +414,7 @@ public:
ZeroOrMore(const std::shared_ptr<Rule>& rule) : rule_(rule) {} ZeroOrMore(const std::shared_ptr<Rule>& rule) : rule_(rule) {}
template <typename T> template <typename T>
Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const; Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const;
private: private:
std::shared_ptr<Rule> rule_; std::shared_ptr<Rule> rule_;
@ -426,7 +426,7 @@ public:
OneOrMore(const std::shared_ptr<Rule>& rule) : rule_(rule) {} OneOrMore(const std::shared_ptr<Rule>& rule) : rule_(rule) {}
template <typename T> template <typename T>
Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const; Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const;
private: private:
std::shared_ptr<Rule> rule_; std::shared_ptr<Rule> rule_;
@ -438,7 +438,7 @@ public:
Option(const std::shared_ptr<Rule>& rule) : rule_(rule) {} Option(const std::shared_ptr<Rule>& rule) : rule_(rule) {}
template <typename T> template <typename T>
Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const; Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const;
private: private:
std::shared_ptr<Rule> rule_; std::shared_ptr<Rule> rule_;
@ -450,7 +450,7 @@ public:
AndPredicate(const std::shared_ptr<Rule>& rule) : rule_(rule) {} AndPredicate(const std::shared_ptr<Rule>& rule) : rule_(rule) {}
template <typename T> template <typename T>
Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const; Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const;
private: private:
std::shared_ptr<Rule> rule_; std::shared_ptr<Rule> rule_;
@ -462,7 +462,7 @@ public:
NotPredicate(const std::shared_ptr<Rule>& rule) : rule_(rule) {} NotPredicate(const std::shared_ptr<Rule>& rule) : rule_(rule) {}
template <typename T> template <typename T>
Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const; Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const;
private: private:
std::shared_ptr<Rule> rule_; std::shared_ptr<Rule> rule_;
@ -474,7 +474,7 @@ public:
LiteralString(const char* s) : lit_(s) {} LiteralString(const char* s) : lit_(s) {}
template <typename T> template <typename T>
Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const { Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const {
auto i = 0u; auto i = 0u;
for (; i < lit_.size(); i++) { for (; i < lit_.size(); i++) {
if (i >= l || s[i] != lit_[i]) { if (i >= l || s[i] != lit_[i]) {
@ -494,7 +494,7 @@ public:
CharacterClass(const char* chars) : chars_(chars) {} CharacterClass(const char* chars) : chars_(chars) {}
template <typename T> template <typename T>
Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const { Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const {
if (l < 1) { if (l < 1) {
return fail(); return fail();
} }
@ -526,7 +526,7 @@ public:
Character(char ch) : ch_(ch) {} Character(char ch) : ch_(ch) {}
template <typename T> template <typename T>
Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const { Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const {
if (l < 1 || s[0] != ch_) { if (l < 1 || s[0] != ch_) {
return fail(); return fail();
} }
@ -541,7 +541,7 @@ class AnyCharacter
{ {
public: public:
template <typename T> template <typename T>
Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const { Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const {
if (l < 1) { if (l < 1) {
return fail(); return fail();
} }
@ -555,7 +555,7 @@ public:
Grouping(const std::shared_ptr<Rule>& rule) : rule_(rule) {} Grouping(const std::shared_ptr<Rule>& rule) : rule_(rule) {}
template <typename T> template <typename T>
Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const; Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const;
private: private:
std::shared_ptr<Rule> rule_; std::shared_ptr<Rule> rule_;
@ -567,14 +567,11 @@ public:
NonTerminal(Definition* outer) : outer_(outer) {}; NonTerminal(Definition* outer) : outer_(outer) {};
template <typename T> template <typename T>
Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const; Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const;
private: private:
friend class Definition; friend class Definition;
template<typename T, typename Action>
void reduce(SemanticStack<T>& ss, const char* s, size_t l, Action action) const;
template<typename T, typename Action> template<typename T, typename Action>
T reduce(const char* s, size_t l, const std::vector<T>& v, const std::vector<std::string>& n, Action action) const; T reduce(const char* s, size_t l, const std::vector<T>& v, const std::vector<std::string>& n, Action action) const;
@ -591,7 +588,7 @@ public:
, name_(name) {} , name_(name) {}
template <typename T> template <typename T>
Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const; Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const;
private: private:
const std::map<std::string, Definition>& grammar_; const std::map<std::string, Definition>& grammar_;
@ -604,7 +601,7 @@ public:
WeakHolder(const std::shared_ptr<Rule>& rule) : weak_(rule) {} WeakHolder(const std::shared_ptr<Rule>& rule) : weak_(rule) {}
template <typename T> template <typename T>
Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const; Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const;
private: private:
std::weak_ptr<Rule> weak_; std::weak_ptr<Rule> weak_;
@ -624,23 +621,23 @@ public:
TRule(T&& val) : vt(std::move(val)) {} TRule(T&& val) : vt(std::move(val)) {}
template <typename T> template <typename T>
Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const { Match parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const {
switch (vt.type_index) { switch (vt.type_index) {
case 0: return vt.template get<Sequence>().template parse<T>(s, l, sa, ss); case 0: return vt.template get<Sequence>().template parse<T>(s, l, sa, sv);
case 1: return vt.template get<PrioritizedChoice>().template parse<T>(s, l, sa, ss); case 1: return vt.template get<PrioritizedChoice>().template parse<T>(s, l, sa, sv);
case 2: return vt.template get<ZeroOrMore>().template parse<T>(s, l, sa, ss); case 2: return vt.template get<ZeroOrMore>().template parse<T>(s, l, sa, sv);
case 3: return vt.template get<OneOrMore>().template parse<T>(s, l, sa, ss); case 3: return vt.template get<OneOrMore>().template parse<T>(s, l, sa, sv);
case 4: return vt.template get<Option>().template parse<T>(s, l, sa, ss); case 4: return vt.template get<Option>().template parse<T>(s, l, sa, sv);
case 5: return vt.template get<AndPredicate>().template parse<T>(s, l, sa, ss); case 5: return vt.template get<AndPredicate>().template parse<T>(s, l, sa, sv);
case 6: return vt.template get<NotPredicate>().template parse<T>(s, l, sa, ss); case 6: return vt.template get<NotPredicate>().template parse<T>(s, l, sa, sv);
case 7: return vt.template get<LiteralString>().template parse<T>(s, l, sa, ss); case 7: return vt.template get<LiteralString>().template parse<T>(s, l, sa, sv);
case 8: return vt.template get<CharacterClass>().template parse<T>(s, l, sa, ss); case 8: return vt.template get<CharacterClass>().template parse<T>(s, l, sa, sv);
case 9: return vt.template get<Character>().template parse<T>(s, l, sa, ss); case 9: return vt.template get<Character>().template parse<T>(s, l, sa, sv);
case 10: return vt.template get<AnyCharacter>().template parse<T>(s, l, sa, ss); case 10: return vt.template get<AnyCharacter>().template parse<T>(s, l, sa, sv);
case 11: return vt.template get<Grouping>().template parse<T>(s, l, sa, ss); case 11: return vt.template get<Grouping>().template parse<T>(s, l, sa, sv);
case 12: return vt.template get<NonTerminal>().template parse<T>(s, l, sa, ss); case 12: return vt.template get<NonTerminal>().template parse<T>(s, l, sa, sv);
case 13: return vt.template get<DefinitionReference>().template parse<T>(s, l, sa, ss); case 13: return vt.template get<DefinitionReference>().template parse<T>(s, l, sa, sv);
case 14: return vt.template get<WeakHolder>().template parse<T>(s, l, sa, ss); case 14: return vt.template get<WeakHolder>().template parse<T>(s, l, sa, sv);
} }
throw std::logic_error("couldn't find the internal data in the variant..."); throw std::logic_error("couldn't find the internal data in the variant...");
@ -849,11 +846,10 @@ struct SemanticActions : public std::map<void*, SemanticActionAdaptor<T>>
}; };
template <typename T> template <typename T>
struct SemanticStack struct SemanticValues
{ {
SemanticStack() : values(1), names(1) {} std::vector<std::string> names;
std::vector<std::vector<std::string>> names; std::vector<T> values;
std::vector<std::vector<T>> values;
}; };
/* /*
@ -902,13 +898,13 @@ public:
template <typename T> template <typename T>
bool parse(const char* s, size_t l, const SemanticActions<T>& sa, T& val) const { bool parse(const char* s, size_t l, const SemanticActions<T>& sa, T& val) const {
SemanticStack<T> ss; SemanticValues<T> sv;
auto m = rule_->parse<T>(s, l, &sa, &ss); auto m = rule_->parse<T>(s, l, &sa, &sv);
auto ret = m.ret && m.len == l; auto ret = m.ret && m.len == l;
if (ret && !ss.values.empty() && !ss.values[0].empty()) { if (ret && !sv.values.empty()) {
val = ss.values[0][0]; val = sv.values[0];
} }
return ret; return ret;
@ -949,10 +945,10 @@ private:
* Implementation * Implementation
*/ */
template <typename T> template <typename T>
Match Sequence::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const { Match Sequence::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const {
size_t i = 0; size_t i = 0;
for (const auto& rule : rules_) { for (const auto& rule : rules_) {
auto m = rule->parse<T>(s + i, l - i, sa, ss); auto m = rule->parse<T>(s + i, l - i, sa, sv);
if (!m.ret) { if (!m.ret) {
return fail(); return fail();
} }
@ -962,9 +958,9 @@ Match Sequence::parse(const char* s, size_t l, const SemanticActions<T>* sa, Sem
} }
template <typename T> template <typename T>
Match PrioritizedChoice::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const { Match PrioritizedChoice::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const {
for (const auto& rule : rules_) { for (const auto& rule : rules_) {
auto m = rule->parse<T>(s, l, sa, ss); auto m = rule->parse<T>(s, l, sa, sv);
if (m.ret) { if (m.ret) {
return success(m.len); return success(m.len);
} }
@ -973,10 +969,10 @@ Match PrioritizedChoice::parse(const char* s, size_t l, const SemanticActions<T>
} }
template <typename T> template <typename T>
Match ZeroOrMore::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const { Match ZeroOrMore::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const {
auto i = 0; auto i = 0;
while (l - i > 0) { while (l - i > 0) {
auto m = rule_->parse<T>(s + i, l - i, sa, ss); auto m = rule_->parse<T>(s + i, l - i, sa, sv);
if (!m.ret) { if (!m.ret) {
break; break;
} }
@ -986,14 +982,14 @@ Match ZeroOrMore::parse(const char* s, size_t l, const SemanticActions<T>* sa, S
} }
template <typename T> template <typename T>
Match OneOrMore::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const { Match OneOrMore::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const {
auto m = rule_->parse<T>(s, l, sa, ss); auto m = rule_->parse<T>(s, l, sa, sv);
if (!m.ret) { if (!m.ret) {
return fail(); return fail();
} }
auto i = m.len; auto i = m.len;
while (l - i > 0) { while (l - i > 0) {
auto m = rule_->parse<T>(s + i, l - i, sa, ss); auto m = rule_->parse<T>(s + i, l - i, sa, sv);
if (!m.ret) { if (!m.ret) {
break; break;
} }
@ -1003,14 +999,14 @@ Match OneOrMore::parse(const char* s, size_t l, const SemanticActions<T>* sa, Se
} }
template <typename T> template <typename T>
Match Option::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const { Match Option::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const {
auto m = rule_->parse<T>(s, l, sa, ss); auto m = rule_->parse<T>(s, l, sa, sv);
return success(m.ret ? m.len : 0); return success(m.ret ? m.len : 0);
} }
template <typename T> template <typename T>
Match AndPredicate::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const { Match AndPredicate::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const {
auto m = rule_->parse<T>(s, l, sa, ss); auto m = rule_->parse<T>(s, l, sa, sv);
if (m.ret) { if (m.ret) {
return success(0); return success(0);
} else { } else {
@ -1019,8 +1015,8 @@ Match AndPredicate::parse(const char* s, size_t l, const SemanticActions<T>* sa,
} }
template <typename T> template <typename T>
Match NotPredicate::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const { Match NotPredicate::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const {
auto m = rule_->parse<T>(s, l, sa, ss); auto m = rule_->parse<T>(s, l, sa, sv);
if (m.ret) { if (m.ret) {
return fail(); return fail();
} else { } else {
@ -1029,29 +1025,29 @@ Match NotPredicate::parse(const char* s, size_t l, const SemanticActions<T>* sa,
} }
template <typename T> template <typename T>
Match Grouping::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const { Match Grouping::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const {
assert(rule_); assert(rule_);
return rule_->parse<T>(s, l, sa, ss); return rule_->parse<T>(s, l, sa, sv);
} }
template <typename T> template <typename T>
Match NonTerminal::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const { Match NonTerminal::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const {
if (!rule_) { if (!rule_) {
throw std::logic_error("Uninitialized definition rule was used..."); throw std::logic_error("Uninitialized definition rule was used...");
} }
if (ss) { std::unique_ptr<SemanticValues<T>> chldsv;
ss->values.push_back(std::vector<T>()); if (sv) {
ss->names.push_back(std::vector<std::string>()); chldsv.reset(new SemanticValues<T>());
} }
auto m = rule_->parse<T>(s, l, sa, ss); auto m = rule_->parse<T>(s, l, sa, chldsv.get());
if (m.ret) { if (m.ret) {
if (outer_->match) { if (outer_->match) {
outer_->match(s, m.len); outer_->match(s, m.len);
} }
typedef std::function<T(const char* s, size_t l, const std::vector<T>& v, const std::vector<std::string>& n)> Action; typedef std::function<T (const char* s, size_t l, const std::vector<T>& v, const std::vector<std::string>& n)> Action;
Action action; Action action;
if (sa) { if (sa) {
@ -1061,25 +1057,16 @@ Match NonTerminal::parse(const char* s, size_t l, const SemanticActions<T>* sa,
} }
} }
if (ss) { if (sv) {
reduce<T>(*ss, s, m.len, action); sv->names.push_back(outer_->name);
auto val = reduce<T>(s, m.len, chldsv->values, chldsv->names, action);
sv->values.push_back(val);
} }
} }
if (ss) {
ss->names.pop_back();
ss->values.pop_back();
}
return m; return m;
} }
template<typename T, typename Action>
void NonTerminal::reduce(SemanticStack<T>& ss, const char* s, size_t l, Action action) const {
ss.names[ss.names.size() - 2].push_back(outer_->name);
ss.values[ss.values.size() - 2].push_back(reduce<T>(s, l, ss.values.back(), ss.names.back(), action));
}
template<typename T, typename Action> template<typename T, typename Action>
T NonTerminal::reduce(const char* s, size_t l, const std::vector<T>& v, const std::vector<std::string>& n, Action action) const { T NonTerminal::reduce(const char* s, size_t l, const std::vector<T>& v, const std::vector<std::string>& n, Action action) const {
if (action) { if (action) {
@ -1092,16 +1079,16 @@ T NonTerminal::reduce(const char* s, size_t l, const std::vector<T>& v, const st
} }
template <typename T> template <typename T>
Match WeakHolder::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const { Match WeakHolder::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const {
auto rule = weak_.lock(); auto rule = weak_.lock();
assert(rule); assert(rule);
return rule->parse<T>(s, l, sa, ss); return rule->parse<T>(s, l, sa, sv);
} }
template <typename T> template <typename T>
Match DefinitionReference::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticStack<T>* ss) const { Match DefinitionReference::parse(const char* s, size_t l, const SemanticActions<T>* sa, SemanticValues<T>* sv) const {
auto rule = grammar_.at(name_).rule_; auto rule = grammar_.at(name_).rule_;
return rule->parse<T>(s, l, sa, ss); return rule->parse<T>(s, l, sa, sv);
} }
/* /*