예제 #1
0
 private static string GetFirstSymbol(Bamboo.Parsing.Grammars.Expression expression)
 {
     if (expression is Bamboo.Parsing.Grammars.Symbol)
     {
         Bamboo.Parsing.Grammars.Symbol symbol = (Bamboo.Parsing.Grammars.Symbol)expression;
         return(symbol.Token);
     }
     else if (expression is Bamboo.Parsing.Grammars.Concatenation)
     {
         Bamboo.Parsing.Grammars.Concatenation concatenation = (Bamboo.Parsing.Grammars.Concatenation)expression;
         return(GetFirstSymbol(concatenation.Expressions[0]));
     }
     else
     {
         throw new System.Exception("INVALID");
     }
 }
예제 #2
0
        private static List <Bamboo.Parsing.Grammars.Expression> ToList(Bamboo.Parsing.Grammars.Expression expression)
        {
            List <Bamboo.Parsing.Grammars.Expression> list = new List <Bamboo.Parsing.Grammars.Expression>();

            if (expression is Bamboo.Parsing.Grammars.Symbol)
            {
                Bamboo.Parsing.Grammars.Symbol symbol = (Bamboo.Parsing.Grammars.Symbol)expression;
                list.Add(symbol);
            }
            else if (expression is Bamboo.Parsing.Grammars.Concatenation)
            {
                Bamboo.Parsing.Grammars.Concatenation concatenation = (Bamboo.Parsing.Grammars.Concatenation)expression;
                foreach (Bamboo.Parsing.Grammars.Symbol symbol in concatenation.Expressions)
                {
                    list.Add(symbol);
                }
            }
            else
            {
                throw new System.Exception("INVALID");
            }
            return(list);
        }
예제 #3
0
 private static bool CanResolve(Bamboo.Parsing.Grammars.Expression expression, List <Bamboo.Parsing.Grammars.Production> remaining)
 {
     if (expression is Bamboo.Parsing.Grammars.Symbol)
     {
         Bamboo.Parsing.Grammars.Symbol symbol = (Bamboo.Parsing.Grammars.Symbol)expression;
         foreach (Bamboo.Parsing.Grammars.Production production in remaining)
         {
             if (production.Nonterminal.Equals(symbol.Token))
             {
                 return(false);
             }
         }
         return(true);
     }
     else if (expression is Bamboo.Parsing.Grammars.Concatenation)
     {
         Bamboo.Parsing.Grammars.Concatenation concatenation = (Bamboo.Parsing.Grammars.Concatenation)expression;
         return(CanResolve(concatenation.Expressions[0], remaining));
     }
     else
     {
         throw new System.Exception("INVALID");
     }
 }
예제 #4
0
        public static void Generate(string name, string nspace, Bamboo.Parsing.Grammars.Grammar grammar, System.IO.TextWriter writer)
        {
            writer.WriteLine("//");
            writer.WriteLine("// AUTOGENERATED " + System.DateTime.Now + "");
            writer.WriteLine("//");
            writer.WriteLine("using System;");
            writer.WriteLine("");
            writer.WriteLine("namespace " + nspace + "");
            writer.WriteLine("{");
            writer.WriteLine("	public abstract class "+ name + "Evaluator");
            writer.WriteLine("	{");
            writer.WriteLine("");
            writer.WriteLine("		public "+ name + "Evaluator()");
            writer.WriteLine("		{");
            writer.WriteLine("		}");
            writer.WriteLine("");
            writer.WriteLine("		public object Evaluate("+ name + "Node node)");
            writer.WriteLine("		{");
            writer.WriteLine("			switch (node.Type)");
            writer.WriteLine("			{");
            foreach (string nonterminal in grammar.Nonterminals)
            {
                writer.WriteLine("				case "+ name + "NodeType." + nonterminal + ":");
                writer.WriteLine("					{");
                foreach (Bamboo.Parsing.Grammars.Production production in GetProductions(nonterminal, grammar))
                {
                    if (production.Expression is Bamboo.Parsing.Grammars.Concatenation)
                    {
                        Bamboo.Parsing.Grammars.Concatenation concatenation = (Bamboo.Parsing.Grammars.Concatenation)production.Expression;

                        string tag = "";

                        writer.Write("						if(");
                        writer.Write("node.Nodes.Count == " + concatenation.Expressions.Count);
                        int i = 0;
                        foreach (Bamboo.Parsing.Grammars.Symbol symbol in concatenation.Expressions)
                        {
                            tag += symbol.Token;
                            writer.Write(" && node.Nodes[" + i + "].Type == " + name + "NodeType." + symbol.Token + "");
                            i++;
                        }

                        writer.WriteLine(")");
                        writer.WriteLine("						{");
                        writer.WriteLine("							return Evaluate"+ tag + "(node);");
                        writer.WriteLine("						}");
                    }
                    else if (production.Expression is Bamboo.Parsing.Grammars.Symbol)
                    {
                        Bamboo.Parsing.Grammars.Symbol symbol = (Bamboo.Parsing.Grammars.Symbol)production.Expression;

                        if (!symbol.Token.Equals("EPSILON"))
                        {
                            string tag = symbol.Token;

                            writer.Write("						if(");
                            writer.Write("node.Nodes.Count == 1");
                            writer.Write(" && node.Nodes[0].Type == " + name + "NodeType." + symbol.Token + "");
                            writer.WriteLine(")");
                            writer.WriteLine("						{");
                            if (grammar.Terminals.Contains(symbol.Token))
                            {
                                writer.WriteLine("							return Evaluate"+ tag + "(node.Nodes[0].Value);");
                            }
                            else
                            {
                                writer.WriteLine("							return Evaluate"+ tag + "(node.Nodes[0]);");
                            }
                            writer.WriteLine("						}");
                        }
                    }
                    else
                    {
                        throw new System.Exception("Invalid expression.");
                    }
                }
                writer.WriteLine("						throw new System.Exception(\"Invalid expression.\");");
                writer.WriteLine("					}");
            }
            foreach (string terminal in grammar.Terminals)
            {
                if (!terminal.Equals("EPSILON"))
                {
                    writer.WriteLine("				case "+ name + "NodeType." + terminal + ":");
                    writer.WriteLine("					{");
                    writer.WriteLine("						return Evaluate"+ terminal + "(node.Value);");
                    writer.WriteLine("					}");
                }
            }
            writer.WriteLine("				default:");
            writer.WriteLine("					{");
            writer.WriteLine("						throw new System.Exception(\"Invalid expression.\");");
            writer.WriteLine("					}");
            writer.WriteLine("			}");
            writer.WriteLine("		}");
            writer.WriteLine("");
            Surf.Set functions = new Surf.Set();
            functions.Define("EPSILON", "EPSILON");
            foreach (string nonterminal in grammar.Nonterminals)
            {
                foreach (Bamboo.Parsing.Grammars.Production production in GetProductions(nonterminal, grammar))
                {
                    string tag = "";

                    if (production.Expression is Bamboo.Parsing.Grammars.Concatenation)
                    {
                        Bamboo.Parsing.Grammars.Concatenation concatenation = (Bamboo.Parsing.Grammars.Concatenation)production.Expression;

                        foreach (Bamboo.Parsing.Grammars.Symbol symbol in concatenation.Expressions)
                        {
                            tag += symbol.Token;
                        }
                        if (!functions.IsDefined(tag))
                        {
                            writer.WriteLine("		protected virtual object Evaluate"+ tag + "(" + name + "Node node)");
                            writer.WriteLine("		{");
                            writer.WriteLine("			throw new System.Exception(\"Implement.\");");
                            writer.WriteLine("		}");
                            writer.WriteLine("");
                            functions.Define(tag, tag);
                        }
                    }
                    else if (production.Expression is Bamboo.Parsing.Grammars.Symbol)
                    {
                        Bamboo.Parsing.Grammars.Symbol symbol = (Bamboo.Parsing.Grammars.Symbol)production.Expression;

                        tag += symbol.Token;
                        if (!functions.IsDefined(tag))
                        {
                            if (grammar.Terminals.Contains(symbol.Token))
                            {
                                writer.WriteLine("		protected virtual object Evaluate"+ tag + "(string value)");
                            }
                            else
                            {
                                writer.WriteLine("		protected virtual object Evaluate"+ tag + "(" + name + "Node node)");
                            }
                            writer.WriteLine("		{");
                            writer.WriteLine("			throw new System.Exception(\"Implement.\");");
                            writer.WriteLine("		}");
                            writer.WriteLine("");
                            functions.Define(tag, tag);
                        }
                    }
                    else
                    {
                        throw new System.Exception("Invalid expression.");
                    }
                }
            }
            foreach (string terminal in grammar.Terminals)
            {
                if (!functions.IsDefined(terminal))
                {
                    writer.WriteLine("		protected virtual object Evaluate"+ terminal + "(string value)");
                    writer.WriteLine("		{");
                    writer.WriteLine("			throw new System.Exception(\"Implement.\");");
                    writer.WriteLine("		}");
                    writer.WriteLine("");
                    functions.Define(terminal, terminal);
                }
            }
            writer.WriteLine("	}");
            writer.WriteLine("}");
        }
예제 #5
0
        public static void GenerateClass(string name, string multinamespace, Bamboo.Parsing.Grammars.Grammar grammar, Surf.Set FIRST, Surf.Set FOLLOW, Surf.Set PREDICT, System.IO.TextWriter writer)
        {
            writer.WriteLine("//");
            writer.WriteLine("// " + name + "Parser.cpp");
            writer.WriteLine("//");
            writer.WriteLine("// AUTOGENERATED " + System.DateTime.Now + "");
            writer.WriteLine("//");
            writer.WriteLine("");
            writer.WriteLine("#include <istream>");
            writer.WriteLine("#include <sstream>");
            writer.WriteLine("#include <string>");
            writer.WriteLine("#include <vector>");
            writer.WriteLine("#include \"" + name + "Parser.h\"");
            writer.WriteLine("#include \"" + name + "Token.h\"");
            writer.WriteLine("#include \"" + name + "TokenType.h\"");
            writer.WriteLine("");

            string[] namespaces = multinamespace.Split(new string[] { "::" }, StringSplitOptions.None);
            foreach (string nspace in namespaces)
            {
                writer.WriteLine("namespace " + nspace + "");
                writer.WriteLine("{");
            }

            writer.WriteLine("	void Parser::next("+ name + "Token& token)");
            writer.WriteLine("	{");
            writer.WriteLine("	start:");
            writer.WriteLine("		switch(_currentState)");
            writer.WriteLine("		{");

            Dictionary <string, int> states = new Dictionary <string, int>();
            int state = 0;

            foreach (string nonterminal in grammar.Nonterminals)
            {
                states.Add(nonterminal, state++);
            }
            foreach (string terminal in grammar.Terminals)
            {
                if (terminal != "EPSILON")
                {
                    states.Add(terminal, state++);
                }
            }

            foreach (string nonterminal in grammar.Nonterminals)
            {
                bool hasDefault = false;

                writer.WriteLine("		case "+ states[nonterminal] + ": // parse" + nonterminal);
                writer.WriteLine("			{");
                writer.WriteLine("				switch(token.type())");
                writer.WriteLine("				{");

                int state2 = state;
                foreach (Surf.Tuple tuple in PREDICT)
                {
                    int n = (int)tuple[0] + 1;
                    Bamboo.Parsing.Grammars.Production production = (Bamboo.Parsing.Grammars.Production)tuple[1];
                    Surf.Set predict = (Surf.Set)tuple[2];

                    if (production.Nonterminal.Equals(nonterminal))
                    {
                        foreach (string symbol in predict)
                        {
                            List <Bamboo.Parsing.Grammars.Expression> expressions = ToList(production.Expression);
                            if (expressions.Count == 1 && ((Bamboo.Parsing.Grammars.Symbol)expressions[0]).Token == "EPSILON")
                            {
                                hasDefault = true;
                            }
                            else
                            {
                                writer.WriteLine("				case TokenType::"+ symbol + ":");
                                writer.WriteLine("					{");

                                writer.Write("						beginParse"+ nonterminal);
                                foreach (Bamboo.Parsing.Grammars.Symbol expression in expressions)
                                {
                                    writer.Write("_" + expression.Token);
                                }
                                writer.WriteLine("();");

                                writer.Write("						_states.push_back("+ state2++ + "); // endParse" + nonterminal);
                                foreach (Bamboo.Parsing.Grammars.Symbol expression in expressions)
                                {
                                    writer.Write("_" + expression.Token);
                                }
                                writer.WriteLine("();");
                                for (int i = (expressions.Count - 1); i >= 1; i--)
                                {
                                    Bamboo.Parsing.Grammars.Symbol expression = (Bamboo.Parsing.Grammars.Symbol)expressions[i];
                                    writer.WriteLine("						_states.push_back("+ states[expression.Token] + "); // parse" + expression.Token);
                                }
                                Bamboo.Parsing.Grammars.Symbol expression2 = (Bamboo.Parsing.Grammars.Symbol)expressions[0];
                                writer.WriteLine("						_currentState = "+ states[expression2.Token] + "; // parse" + expression2.Token);
                                writer.WriteLine("						goto start;");
                                writer.WriteLine("						break;");
                                writer.WriteLine("					}");
                            }
                        }
                    }
                }

                if (states[nonterminal] == 0)
                {
                    writer.WriteLine("				case "+ name + "TokenType::_EOF_:");
                    writer.WriteLine("					{");
                    writer.WriteLine("						if (_states.size() > 0)");
                    writer.WriteLine("						{");
                    writer.WriteLine("							_currentState = _states.back();");
                    writer.WriteLine("							_states.pop_back();");
                    writer.WriteLine("							goto start;");
                    writer.WriteLine("						}");
                    writer.WriteLine("						break;");
                    writer.WriteLine("					}");
                }

                if (hasDefault)
                {
                    writer.WriteLine("				default:");
                    writer.WriteLine("					{");
                    writer.WriteLine("						// EPSILON");
                    writer.WriteLine("						_currentState = _states.back();");
                    writer.WriteLine("						_states.pop_back();");
                    writer.WriteLine("						goto start;");
                    writer.WriteLine("					}");
                }
                else
                {
                    writer.WriteLine("				default:");
                    writer.WriteLine("					{");
                    writer.WriteLine("						std::stringstream stream;");
                    writer.WriteLine("						stream << __FILE__ << \" \" << __LINE__ << \" \" << \"Syntax error.\";");
                    writer.WriteLine("						throw stream.str();");
                    writer.WriteLine("					}");
                }
                writer.WriteLine("				}");
                writer.WriteLine("				break;");
                writer.WriteLine("			}");



                state2 = state;
                foreach (Surf.Tuple tuple in PREDICT)
                {
                    int n = (int)tuple[0] + 1;
                    Bamboo.Parsing.Grammars.Production production = (Bamboo.Parsing.Grammars.Production)tuple[1];
                    Surf.Set predict = (Surf.Set)tuple[2];

                    if (production.Nonterminal.Equals(nonterminal))
                    {
                        foreach (string symbol in predict)
                        {
                            List <Bamboo.Parsing.Grammars.Expression> expressions = ToList(production.Expression);
                            if (expressions.Count == 1 && ((Bamboo.Parsing.Grammars.Symbol)expressions[0]).Token == "EPSILON")
                            {
                            }
                            else
                            {
                                writer.Write("		case "+ state2++ + ": // endParse" + nonterminal);
                                foreach (Bamboo.Parsing.Grammars.Symbol expression in expressions)
                                {
                                    writer.Write("_" + expression.Token);
                                }
                                writer.WriteLine("();");
                                writer.WriteLine("			{");
                                writer.Write("				"+ "endParse" + nonterminal);
                                foreach (Bamboo.Parsing.Grammars.Symbol expression in expressions)
                                {
                                    writer.Write("_" + expression.Token);
                                }
                                writer.WriteLine("();");
                                writer.WriteLine("				if (_states.size() == 0)");
                                writer.WriteLine("				{");
                                writer.WriteLine("					_currentState = 0;");
                                writer.WriteLine("				}");
                                writer.WriteLine("				else");
                                writer.WriteLine("				{");
                                writer.WriteLine("					_currentState = _states.back();");
                                writer.WriteLine("					_states.pop_back();");
                                writer.WriteLine("				}");
                                writer.WriteLine("				goto start;");
                                writer.WriteLine("				break;");
                                writer.WriteLine("			}");
                            }
                        }
                    }
                }

                state = state2;
            }
            foreach (string terminal in grammar.Terminals)
            {
                if (terminal != "EPSILON")
                {
                    writer.WriteLine("		case "+ states[terminal] + ": // " + terminal);
                    writer.WriteLine("			{");
                    writer.WriteLine("				parse"+ terminal + "(token);");
                    writer.WriteLine("				if (_states.size() == 0)");
                    writer.WriteLine("				{");
                    writer.WriteLine("					_currentState = 0;");
                    writer.WriteLine("				}");
                    writer.WriteLine("				else");
                    writer.WriteLine("				{");
                    writer.WriteLine("					_currentState = _states.back();");
                    writer.WriteLine("					_states.pop_back();");
                    writer.WriteLine("				}");
                    writer.WriteLine("				break;");
                    writer.WriteLine("			}");
                }
            }

            writer.WriteLine("		default:");
            writer.WriteLine("			{");
            writer.WriteLine("				std::stringstream stream;");
            writer.WriteLine("				stream << __FILE__ << \" \" << __LINE__ << \" \" << \"Invalid parser state.\";");
            writer.WriteLine("				throw stream.str();");
            writer.WriteLine("			}");
            writer.WriteLine("		}");
            writer.WriteLine("	}");
            writer.WriteLine("");

            foreach (string nspace in namespaces)
            {
                writer.WriteLine("}");
            }
        }