Algorithms Library Toolkit
A toolkit for algorithms, especially for algorithms on formal languages
All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Concepts
ToGNF.h
Go to the documentation of this file.
1
6#pragma once
7
8#include <ext/algorithm>
9
10#include <alib/map>
11
21
22#include "EpsilonRemover.h"
23#include "SimpleRulesRemover.h"
27
28namespace grammar {
29
30namespace simplify {
31
36class ToGNF {
37 template < class TerminalSymbolType, class NonterminalSymbolType >
39 template < class TerminalSymbolType, class NonterminalSymbolType >
41
42public:
53 template < class TerminalSymbolType, class NonterminalSymbolType >
55
66 template < class TerminalSymbolType, class NonterminalSymbolType >
68
79 template < class TerminalSymbolType, class NonterminalSymbolType >
81
92 template < class TerminalSymbolType, class NonterminalSymbolType >
94
105 template < class TerminalSymbolType, class NonterminalSymbolType >
107
118 template < class TerminalSymbolType, class NonterminalSymbolType >
120
131 template < class TerminalSymbolType, class NonterminalSymbolType >
133
144 template < class TerminalSymbolType, class NonterminalSymbolType >
146
157 template < class TerminalSymbolType, class NonterminalSymbolType >
159};
160
161template < class TerminalSymbolType, class NonterminalSymbolType >
164 res.setNonterminalAlphabet(grammar.getNonterminalAlphabet());
165 res.setTerminalAlphabet(grammar.getTerminalAlphabet());
166 res.setGeneratesEpsilon(grammar.getGeneratesEpsilon());
167
168 for ( const std::pair < const NonterminalSymbolType, ext::set<ext::vector<ext::variant < TerminalSymbolType, NonterminalSymbolType > > > > & rule : grammar.getRules ( ) ) {
169 for(const ext::vector < ext::variant < TerminalSymbolType, NonterminalSymbolType > > & singleRHS : rule.second) {
170 if(res.getTerminalAlphabet().count(singleRHS[0])) { //do not substitute terminals
171 res.addRule(rule.first, singleRHS);
172 continue;
173 }
174 const ext::variant < TerminalSymbolType, NonterminalSymbolType > & secondLHS = singleRHS[0];
175 if(grammar.getRules().find(secondLHS) == grammar.getRules().end()) { //is there any right hand side to substitue with?
176 //if not well this rule does not generate anything anyway
177 continue;
178 }
179
180 for(const ext::vector < ext::variant < TerminalSymbolType, NonterminalSymbolType > > & secondSingleRHS : grammar.getRules().find(secondLHS)->second) { // do the substitution
182 newRHS.insert(newRHS.end(), singleRHS.begin() + 1, singleRHS.end());
183 res.addRule(rule.first, newRHS);
184 }
185 }
186 }
187 return res;
188}
189
190template < class TerminalSymbolType, class NonterminalSymbolType >
193 while(true) {
195
196 if(step == nextStep) break;
197 step = std::move(nextStep);
198 }
199
201 res.setTerminalAlphabet(step.getTerminalAlphabet());
202 for ( const NonterminalSymbolType & nonterminal : step.getNonterminalAlphabet ( ) )
203 res.addNonterminalSymbol ( ext::variant < TerminalSymbolType, NonterminalSymbolType > ( nonterminal ) );
204 res.setGeneratesEpsilon(step.getGeneratesEpsilon());
206 for ( const TerminalSymbolType & terminal : step.getTerminalAlphabet ( ) ) {
207 ext::variant < TerminalSymbolType, NonterminalSymbolType > primed = common::createUnique ( terminal, res.getTerminalAlphabet(), res.getNonterminalAlphabet());
208 terminalToPrimed.insert(std::make_pair(terminal, primed));
209 res.addNonterminalSymbol(primed);
211 }
212 for(const auto& rule : step.getRules()) {
213 for(const auto& rhs : rule.second) {
215 bool first = true;
217 if(first) {
218 first = false;
219 continue;
220 }
221
222 if(res.getNonterminalAlphabet().count(rhsSymbol))
223 convertedNonterminals.push_back(rhsSymbol);
224 else
225 convertedNonterminals.push_back(terminalToPrimed.find(rhsSymbol)->second);
226 }
227 res.addRule(rule.first, ext::make_pair(rhs[0].template get < TerminalSymbolType > ( ), std::move(convertedNonterminals)));
228 }
229 }
230 return res;
231}
232
233template < class TerminalSymbolType, class NonterminalSymbolType >
236}
237
238template < class TerminalSymbolType, class NonterminalSymbolType >
241}
242
243template < class TerminalSymbolType, class NonterminalSymbolType >
246}
247
248template < class TerminalSymbolType, class NonterminalSymbolType >
250 return grammar;
251}
252
253template < class TerminalSymbolType, class NonterminalSymbolType >
256}
257
258template < class TerminalSymbolType, class NonterminalSymbolType >
261}
262
263template < class TerminalSymbolType, class NonterminalSymbolType >
266}
267
268template < class TerminalSymbolType, class NonterminalSymbolType >
271}
272
273template < class TerminalSymbolType, class NonterminalSymbolType >
275 return grammar;
276}
277
278} /* namespace simplify */
279
280} /* namespace grammar */
281
Class extending the map class from the standard library. Original reason is to allow printing of the ...
Definition: map.hpp:48
std::pair< iterator, bool > insert(const T &key, const R &value)
Insert variant with explicit key and value parameters.
Definition: map.hpp:118
Definition: set.hpp:44
Implementation of the variant class allowing to store any type of those listed in the template parame...
Definition: variant.hpp:98
Class extending the vector class from the standard library. Original reason is to allow printing of t...
Definition: vector.hpp:45
Context free grammar in Chomsky hierarchy or type 2 in Chomsky hierarchy. Generates context free lang...
Definition: CFG.h:67
Chomsky normal form of a context free grammar in Chomsky hierarchy or type 2 in Chomsky hierarchy....
Definition: CNF.h:66
Context free grammar without epsilon rules in Chomsky hierarchy or type 2 in Chomsky hierarchy....
Definition: EpsilonFreeCFG.h:65
Greibach normal form of a context free grammar in Chomsky hierarchy or type 2 in Chomsky hierarchy....
Definition: GNF.h:65
Context free grammar in Chomsky hierarchy or type 2 in Chomsky hierarchy. Generates context free lang...
Definition: LG.h:67
Left linear grammar in Chomsky hierarchy or type 3 in Chomsky hierarchy. Generates regular languages.
Definition: LeftLG.h:66
Left regular grammar in Chomsky hierarchy or type 3 in Chomsky hierarchy. Generates regular languages...
Definition: LeftRG.h:70
Right linear grammar in Chomsky hierarchy or type 3 in Chomsky hierarchy. Generates regular languages...
Definition: RightLG.h:65
Right regular grammar in Chomsky hierarchy or type 3 in Chomsky hierarchy. Generates regular language...
Definition: RightRG.h:70
static grammar::RightRG< TerminalSymbolType, NonterminalSymbolType > convert(const grammar::LeftRG< TerminalSymbolType, NonterminalSymbolType > &grammar)
Definition: ToGrammarRightRG.h:37
static grammar::EpsilonFreeCFG< TerminalSymbolType, NonterminalSymbolType > remove(const grammar::CFG< TerminalSymbolType, NonterminalSymbolType > &grammar)
Definition: EpsilonRemover.h:202
static grammar::EpsilonFreeCFG< TerminalSymbolType, NonterminalSymbolType > remove(const grammar::EpsilonFreeCFG< TerminalSymbolType, NonterminalSymbolType > &grammar)
Definition: LeftRecursionRemover.h:225
static grammar::CFG< TerminalSymbolType, NonterminalSymbolType > remove(const grammar::CFG< TerminalSymbolType, NonterminalSymbolType > &grammar)
Definition: SimpleRulesRemover.h:181
Definition: ToGNF.h:36
static grammar::GNF< TerminalSymbolType, ext::variant< TerminalSymbolType, NonterminalSymbolType > > convert(const grammar::CFG< TerminalSymbolType, NonterminalSymbolType > &grammar)
Definition: ToGNF.h:234
return grammar
Definition: ToGrammarLeftRG.h:99
return res
Definition: MinimizeByPartitioning.h:145
T createUnique(T object, const Alphabets &... alphabets)
Definition: createUnique.hpp:46
constexpr auto make_pair(T1 &&x, T2 &&y)
Definition: pair.hpp:79
Definition: ToAutomaton.h:24