private bool AddClosureItems(ParserState state) { bool result = false; for (int i = 0; i < state.Items.Count; i++) { LRItem item = state.Items[i]; NonTerminal nextNT = item.Core.NextElement as NonTerminal; if (nextNT == null) { continue; } foreach (Production prod in nextNT.Productions) { LR0Item core = prod.LR0Items[0]; LRItem newItem = TryFindItem(state, core); if (newItem == null) { newItem = new LRItem(state, core); state.Items.Add(newItem); result = true; } newItem.NewLookaheads.AddRange(item.Core.TailFirsts); if (item.Core.TailIsNullable && !item.PropagateTargets.Contains(newItem)) { item.PropagateTargets.Add(newItem); } } } return(result); }
private LRItem TryFindItem(ParserState state, LR0Item core) { foreach (LRItem item in state.Items) { if (item.Core == core) { return(item); } } return(null); }
private void CalculateTailFirsts() { foreach (Production prod in _data.Productions) { StringSet accumulatedFirsts = new StringSet(); bool allNullable = true; for (int i = prod.LR0Items.Count - 1; i >= 0; i--) { LR0Item item = prod.LR0Items[i]; if (i >= prod.LR0Items.Count - 2) { item.TailIsNullable = true; item.TailFirsts.Clear(); continue; } GrammarTerm term = prod.RValues[item.Position + 1]; NonTerminal ntElem = term as NonTerminal; if (ntElem == null || !ntElem.Nullable) { accumulatedFirsts.Clear(); allNullable = false; item.TailIsNullable = false; if (ntElem == null) { item.TailFirsts.Add(term.Key); accumulatedFirsts.Add(term.Key); } else { item.TailFirsts.AddRange(ntElem.Firsts); accumulatedFirsts.AddRange(ntElem.Firsts); } continue; } accumulatedFirsts.AddRange(ntElem.Firsts); item.TailFirsts.AddRange(accumulatedFirsts); item.TailIsNullable = allNullable; } } }
private Dictionary <string, LR0ItemList> GetStateShifts(ParserState state) { Dictionary <string, LR0ItemList> shifts = new Dictionary <string, LR0ItemList>(); LR0ItemList list; foreach (LRItem item in state.Items) { GrammarTerm term = item.Core.NextElement; if (term == null) { continue; } LR0Item shiftedItem = item.Core.Production.LR0Items[item.Core.Position + 1]; if (!shifts.TryGetValue(term.Key, out list)) { shifts[term.Key] = list = new LR0ItemList(); } list.Add(shiftedItem); } return(shifts); }
public LRItem(ParserState state, LR0Item core) { State = state; Core = core; }
private LRItem TryFindItem(ParserState state, LR0Item core) { foreach (LRItem item in state.Items) if (item.Core == core) return item; return null; }