// // Created by lenfrex on 2023/5/8. // #include "Grammar.h" using namespace std; // 求是否有交集 bool hasUnion(const set &a, const set &b) { for (const auto &selectChars: b) { if (a.contains(selectChars)) { return true; } } return false; } // 检查是否为LL1文法 bool Grammar::isLL1Grammar() { // 逐个非终止符检查 for (const auto &nonTerminal: nonTerminals) { SelectSet select = selectSet[nonTerminal]; // 取一行 for (auto current = select.begin(); current != select.end();) { const auto &productionSelectSet = current->second; // 取剩下的行进行比较,注意这里已经++current了,外层for就不要++了 for (auto innerCurrent = ++current; innerCurrent != select.end(); innerCurrent++) { if (hasUnion(productionSelectSet, innerCurrent->second)) { return false; } } } } return true; } void Grammar::buildAnalysisTable() { if (!isLL1Grammar()) { throw NotSupportedGrammarException("文法定义不符合LL1文法"); } for (const auto &nonTerminal: nonTerminals) { SelectSet select = selectSet[nonTerminal]; for (const auto &selectPair: select) { const auto &prod = selectPair.first; const auto &selectChars = selectPair.second; // 填充预测分析表 for (const auto &selectableTerminal: selectChars) { analysisTable[nonTerminal][selectableTerminal] = prod; } } } }