TODO : Make RE Grammar template independent. Difine Unified grammar format.

This commit is contained in:
IlyaShurupov 2023-11-02 15:55:55 +03:00 committed by Ilya Shurupov
parent 53b690dad9
commit 419ebb43d1
4 changed files with 115 additions and 11 deletions

View file

@ -1,4 +1,53 @@
#include "Grammar.hpp" #include "Grammar.hpp"
#include "NewPlacement.hpp"
using namespace tp; using namespace tp;
ContextFreeGrammar::Arg::Arg(const String& id, bool terminal, bool epsilon) {
mId = id;
mIsTerminal = terminal;
mIsEpsilon = epsilon;
}
const String& ContextFreeGrammar::Arg::getId() const { return mId; }
bool ContextFreeGrammar::Arg::operator==(const Arg& in) const { return (mId == in.mId) && (mIsEpsilon == in.mIsEpsilon) && (mIsTerminal == in.mIsTerminal); }
ContextFreeGrammar::Rule::Rule(const String& id, const InitialierList<Arg>& args) {
mId = id;
mArgs = args;
}
bool ContextFreeGrammar::Rule::operator==(const Rule& in) const { return (mId == in.mId) && (mArgs == in.mArgs); }
bool ContextFreeGrammar::Rule::isProductive() const {
for (auto arg : mArgs) {
if (arg->getId() == mId) return false;
}
return true;
}
bool ContextFreeGrammar::NonTerminal::isProductive() const {
for (auto rule : rules) {
if (rule->isProductive()) return true;
}
return false;
}
bool ContextFreeGrammar::NonTerminal::isLooped(Map<String, ualni>& processed, const String& id) const {
for (auto ref : referencing) {
if (processed.presents(ref->key)) return true;
}
processed.put(id, {});
for (auto ref : referencing) {
if (ref->val->isLooped(processed, ref->key)) return true;
}
return false;
}
void ContextFreeGrammar::addRule(const Rule& rule) { mRules.append(rule); }
void ContextFreeGrammar::addRule(const String& id, const InitialierList<Arg>& args) { addRule(Rule(id, args)); }
void ContextFreeGrammar::setStart(const String& startRule) { mStartTerminal = startRule; }

View file

@ -12,15 +12,8 @@ SimpleParser::SimpleParser() {
ContextFreeGrammar contextFreeGrammar; ContextFreeGrammar contextFreeGrammar;
{ {
// use existing CF grammar interface // use existing CF grammar interface
auto term = contextFreeGrammar.createTerminal(); contextFreeGrammar.addRule("a", { ContextFreeGrammar::Arg("") });
contextFreeGrammar.setStart("a");
auto nonTerm = contextFreeGrammar.createNonTerminal();
auto nonTerm2 = contextFreeGrammar.createNonTerminal();
contextFreeGrammar.addRule(nonTerm, { term, nonTerm2 });
contextFreeGrammar.addRule();
contextFreeGrammar.setStart(nonTerm);
} }
// Define Regular grammar // Define Regular grammar

View file

@ -3,11 +3,70 @@
#include "Buffer.hpp" #include "Buffer.hpp"
#include "LanguageCommon.hpp" #include "LanguageCommon.hpp"
#include "Utils.hpp" #include "Map.hpp"
#include "Strings.hpp"
namespace tp { namespace tp {
class ContextFreeGrammar {}; class ContextFreeGrammar {
public:
struct Arg {
friend class Rule;
public:
Arg() = default;
explicit Arg(const String& id, bool terminal = true, bool epsilon = false);
public:
bool operator==(const Arg& in) const;
[[nodiscard]] const String& getId() const;
private:
String mId;
bool mIsTerminal = false;
bool mIsEpsilon = false;
};
class Rule {
public:
Rule() = default;
Rule(const String& id, const InitialierList<Arg>& args);
public:
bool operator==(const Rule& in) const;
[[nodiscard]] bool isProductive() const;
private:
String mId;
Buffer<Arg> mArgs;
};
private:
// cache data
struct NonTerminal {
Buffer<Rule*> rules;
Map<String, NonTerminal*> references;
Map<String, NonTerminal*> referencing;
public:
[[nodiscard]] bool isProductive() const;
[[nodiscard]] bool isLooped(Map<String, ualni>& processed, const String& id) const;
};
public:
ContextFreeGrammar() = default;
public:
void addRule(const Rule& rule);
void addRule(const String& id, const InitialierList<Arg>& args);
void setStart(const String& startRule);
private:
Map<String, NonTerminal> mNonTerminals;
Buffer<Rule> mRules;
String mStartTerminal;
bool mIsLooped = false;
};
template <typename tAlphabetType, typename tTokType> template <typename tAlphabetType, typename tTokType>
class RegularGrammar { class RegularGrammar {

3
TODO
View file

@ -3,6 +3,9 @@ All:
make more general structure for feature renders make more general structure for feature renders
Language: Language:
Grammar:
Store all RE Grammar API nodes in one buffer
rename Language module to FormalLanguage rename Language module to FormalLanguage
Merge parser and tokenizer module into grammar module Merge parser and tokenizer module into grammar module