public BuilderHorizonSets(Productions <SYMBOL_ENUM, TREE_NODE> productions, int lookaheadWidth,
                                  FirstSets <SYMBOL_ENUM> firstSets,
                                  CoverSets <SYMBOL_ENUM> coverSets,
                                  FollowSets <SYMBOL_ENUM> followSets)
            : base(productions, lookaheadWidth)
        {
            this.firstSets  = firstSets;
            this.followSets = followSets;
            this.coverSets  = coverSets;

            if (!coverSets.HasNonTerminals || lookaheadWidth != coverSets.LookaheadWidth)
            {
                throw new ArgumentException("Internal error.");
            }
        }
Exemplo n.º 2
0
        private void initFirstSets()
        {
            firstSets = new FirstSets <SYMBOL_ENUM>(lookaheadWidth);

            foreach (SYMBOL_ENUM sym in terminals)
            {
                var set = new SymbolChunkSet <SYMBOL_ENUM>();
                set.Add(SymbolChunk.Create(sym));
                firstSets.Add(sym, set);
            }

            foreach (SYMBOL_ENUM sym in nonTerminals)
            {
                var set = new SymbolChunkSet <SYMBOL_ENUM>();

                // iterate over all productions for this symbol except for error recovery productions
                foreach (Production <SYMBOL_ENUM, TREE_NODE> prod in productions
                         .FilterByLhs(sym)
                         .Where(it => !it.RhsSymbols.Contains(syntaxErrorSymbol)))
                {
                    // we take only terminals from front
                    IEnumerable <SYMBOL_ENUM> first_chunk = prod.RhsSymbols.TakeWhile(it => terminals.Contains(it));
                    int count = first_chunk.Count();

                    if (count >= lookaheadWidth) // we have more than enough
                    {
                        set.Add(SymbolChunk.Create(first_chunk.Take(lookaheadWidth)));
                    }
                    // we have less, but there was no more here
                    else if (count == prod.RhsSymbols.Count)
                    {
                        set.Add(SymbolChunk.Create(first_chunk));
                    }
                }

                firstSets.Add(sym, set);
            }
        }
 public BuilderFollowSets(Productions <SYMBOL_ENUM, TREE_NODE> productions, int lookaheadWidth, FirstSets <SYMBOL_ENUM> firstSets)
     : base(productions, lookaheadWidth)
 {
     this.firstSets = firstSets;
 }