public override void Apply(LanguageData language, LRItem owner)
 {
     var state = owner.State;
     if (!state.BuilderData.IsInadequate) return; //the state is adequate, we don't need to do anything
     var conflicts = state.BuilderData.Conflicts;
     // Note that we remove lookaheads from the state conflicts set at the end of this method - to let parser builder know
     // that this conflict is taken care of. 
     // On the other hand we may call this method multiple times for different LRItems if we have multiple hints in the same state. 
     // Since we remove lookahead from conflicts on the first call, on the consequitive calls it will not be a conflict -
     // but we still need to add a new conditional entry to a conditional parser action for this lookahead. 
     // Thus we process the lookahead anyway, even if it is not a conflict. 
     // if (conflicts.Count == 0) return; -- this is a wrong thing to do
     switch (_actionType)
     {
         case PreferredActionType.Reduce:
             if (!owner.Core.IsFinal) return;
             //it is reduce action; find lookaheads in conflict
             var lkhs = owner.Lookaheads;
             if (lkhs.Count == 0) return; //if no conflicts then nothing to do
             var reduceAction = new ReduceParserAction(owner.Core.Production);
             var reduceCondEntry = new ConditionalParserAction.ConditionalEntry(CheckCondition, reduceAction,
                 _description);
             foreach (var lkh in lkhs)
             {
                 AddConditionalEntry(state, lkh, reduceCondEntry);
                 if (conflicts.Contains(lkh))
                     conflicts.Remove(lkh);
             }
             break;
         case PreferredActionType.Shift:
             var curr = owner.Core.Current as Terminal;
             if (curr == null) return; //it is either reduce item, or curr is a NonTerminal - we cannot shift it
             var shiftAction = new ShiftParserAction(owner);
             var shiftCondEntry = new ConditionalParserAction.ConditionalEntry(CheckCondition, shiftAction,
                 _description);
             AddConditionalEntry(state, curr, shiftCondEntry);
             if (conflicts.Contains(curr))
                 conflicts.Remove(curr);
             break;
     }
 } //method
Example #2
0
 //Check if there is an action already in state for this term; if yes, and it is Conditional action,
 // then simply add an extra conditional entry to it. If an action does not exist, or it is not conditional,
 // create new conditional action for this term.
 private void AddConditionalEntry(ParserState state, BnfTerm term, ConditionalEntry entry)
 {
     ParserAction oldAction;
       ConditionalParserAction condAction = null;
       if (state.Actions.TryGetValue(term, out oldAction))
     condAction = oldAction as ConditionalParserAction;
       if (condAction == null) { //there's no old action, or it is not conditional; create new conditional action
     condAction = new ConditionalParserAction();
     condAction.DefaultAction = oldAction;
     state.Actions[term] = condAction;
       }
       condAction.ConditionalEntries.Add(entry);
       if (condAction.DefaultAction == null)
     condAction.DefaultAction = FindDefaultAction(state, term);
       if (condAction.DefaultAction == null) //if still no action, then use the cond. action as default.
     condAction.DefaultAction = entry.Action;
 }