public void AddFirst(DotItem item, MutableIntSet output) { bool isNullable = tables.AddFirst(item.GetPattern(), item.Position, output); if (isNullable) { output.AddAll(item.LA); } }
public void AddFirst(DotItem item, MutableIntSet output) { bool isNullable = tables.AddFirst(item.GetPattern(), item.Position, output); if (isNullable) { output.AddAll(item.LA); } }
public bool IsTailNullable(DotItem item) { return(tables.IsTailNullable(item.GetPattern(), item.Position)); }
public bool HasFirst(DotItem item, int token) { return(tables.HasFirst(item.GetPattern(), item.Position, token)); }
public DotItem(DotItem other) : this(other.production, other.Position) { }
// TODO: Separate Closure from the lookahead closuring to get cached closure item sets private MutableDotItemSet ClosureLr0(MutableDotItemSet itemSet) { var result = new MutableDotItemSet(); result.AddRange(itemSet); bool modified; do { modified = false; // result may grow during iterations for (int i = 0; i != result.Count; ++i) { var item = result[i]; if (!item.IsReduce && !grammar.IsTerminal(item.NextToken)) { int X = item.NextToken; foreach (var childProd in grammar.GetProductions(X)) { var newItem = new DotItem(childProd, 0) { LA = TokenSet.Mutable() }; var index = result.IndexOf(newItem); if (index < 0) { result.Add(newItem); modified = true; } else { var existing = result[index]; existing.LA.AddAll(newItem.LA); } } } } } while (modified); return result; }
public DotItem(DotItem other) : this(other.production, other.Position) { }
public bool IsTailNullable(DotItem item) { return tables.IsTailNullable(item.GetPattern(), item.Position); }
public bool HasFirst(DotItem item, int token) { return tables.HasFirst(item.GetPattern(), item.Position, token); }
public int IndexOf(DotItem item) { return items.IndexOf(item); }
public void Add(DotItem item) { items.Add(item); }
private bool IsValueOnlyEpsilonReduceItem(DotItem item, DotState state, int lookahead) { if (item.Position != 0 || grammar.IsStartProduction(item.ProductionId) || !grammar.IsTailNullable(item) || !item.LA.Contains(lookahead)) { return false; } int epsilonToken = item.Outcome; foreach (var parentItem in state.Items) { if (parentItem == item) { continue; } if (parentItem.NextToken == epsilonToken) { if (!grammar.IsTailNullable(parentItem)) { // there is at least one rule which needs shift on epsilonToken return false; } if (grammar.HasFirst(parentItem.CreateNextItem(), lookahead)) { // One of the subseqent non-terms in parentItem can start parsing with current lookahead. // It means that we need tested epsilonToken production for continue parsing on parentItem. return false; } } } return true; }