diff options
| author | Roland Reichwein <mail@reichwein.it> | 2020-02-05 21:18:31 +0100 | 
|---|---|---|
| committer | Roland Reichwein <mail@reichwein.it> | 2020-02-05 21:18:31 +0100 | 
| commit | f1b23e34bee172e0c0ed8e65bcd7904baef9e857 (patch) | |
| tree | 36eaccf3ac66c50bad7e583a098f0a931409ae4d | |
| parent | 867f5c29ca2bb1c61797634942fa9f6023a79afe (diff) | |
Fix GetPath
| -rw-r--r-- | grammer.cpp | 51 | 
1 files changed, 20 insertions, 31 deletions
| diff --git a/grammer.cpp b/grammer.cpp index f7a370f..4bdf8f4 100644 --- a/grammer.cpp +++ b/grammer.cpp @@ -268,22 +268,26 @@ std::map<std::string, std::string> Compiler::traverse(lower, upper)   std::deque<std::pair<std::string, std::string>> todo{{lower, ""}}; // node, child   while (!todo.empty()) { -  current = todo.front(); +  auto& [current_node, current_child] = todo.front();    todo.pop_front(); -  if (!visited[current.first]) { -   parents = reverseBNF[current.first]; -    -   visited[current.first] = current.second; -    -   std::for_each(parents.begin(), parents.end(), [&](const auto&x) {todo.emplace_back(x, current.first);}); +  if (!visited[current_node]) { +   auto parents_it {reverseBNF.find(current_node)}; + +   if (parents_it != reverseBNF.end()) { +    auto& parents {parents_it->second}; +     +    visited[current_node] = current_child; +     +    std::for_each(parents.begin(), parents.end(), [&](const auto&x) {todo.emplace_back(x, current_node);}); +   }    }   }   return visited;  } -// returns list from lower (including) to upper (excluding) +// returns list from lower (excluding) to upper (including)  // returns empty list on fail  std::vector<std::string> Compiler::GetPath(std::string upper, std::string lower) {   std::vector<std::string> result; @@ -291,29 +295,13 @@ std::vector<std::string> Compiler::GetPath(std::string upper, std::string lower)   // traverse bnf from lower to upper   std::map<std::string, std::string> visited {traverse(lower, upper)}; - while (lower != upper) { -  auto parents {ReverseBNF.find(lower)}; -  if (parents == ReverseBNF.end()) -   return {}; - -  std::string new_lower; -  bool hit{false}; -  for (const auto& parent : parents->second) { -   for (const auto& list : bnf.at(parent)) { -    if (list.size() > 0 && list[0] == lower) { -     if (!hit) { -      result.push_back(lower); -      new_lower = parent; -      hit = true; -     } else -      throw std::runtime_error("Double match for "s + lower + ": "s + parent + ", "s + new_lower); // TODO: also get alternatives at each step -    } -   } -  } + auto current {upper}; + while (current != lower) { +  auto& child = visited[current]; + +  result.push_back(current); -  if (!hit) -   throw std::runtime_error("GetPath error!"); // ICE -  lower = new_lower; +  current = child;   }   return result;  } @@ -357,7 +345,8 @@ bool Compiler::FillTree()   index_t to_fill;   while (!subTreeIsComplete(root_node_id, to_fill)) { -  auto list = GetPath(nodes[to_fill].type, tokens[tokens_used]); +  auto& node {nodes[to_fill]}; +  auto list = GetPath(bnf[node.type][node.variant][node.child_ids.size()], tokens[tokens_used]);    if (list.size() > 0) {     AddPath(list, to_fill);     return true; | 
