public bool TryInlineCode(Decision decision) { int index = knownDecisions.IndexOf(decision); if (index < 0) { knownDecisions.Insert(generationIndex++, decision); decision.Accept(visitor); return true; } else if (index >= generationIndex) { if (index != generationIndex) { // Swap next planned element and just generated element knownDecisions[index] = knownDecisions[generationIndex]; knownDecisions[generationIndex] = decision; } ++generationIndex; decision.Accept(visitor); return true; } return false; }
public void PlanCode(Decision decision) { if (!knownDecisions.Contains(decision)) { knownDecisions.Add(decision); } }
private Ref<Labels> GetNodeLabel(Decision decision) { if (!decision.Label.HasValue) { decision.Label = labels.Count; labels.Add(emit.Labels.Generate().GetRef()); strategy.PlanCode(decision); } return labels[decision.Label.Value]; }
private void GenerateCodeOrJump(Decision decision) { if (!strategy.TryInlineCode(decision)) { emit.Br(GetNodeLabel(decision)); } }
private int Eval(Decision node, int input) { return node.Decide(input); }
private void PrintProgram(Decision nodes, Decision defaultDecision = null) { if (defaultDecision == null) { defaultDecision = new ActionDecision(-1); } StringBuilder output = new StringBuilder(); var writer = new DecisionProgramWriter(output); writer.Build(nodes, defaultDecision); Debug.WriteLine(output); }
private string GetLabelText(Decision node) { return(FormatLabel(GetLabel(node))); }
private void PutLabel(Decision labelNode) { output.Append(GetLabelText(labelNode)).Append(": "); }
public void Build(Decision root, Decision defaultDecision) { this.defaultDecision = defaultDecision; strategy.PlanCode(root); strategy.GenerateCode(); }
private int GetLabel(Decision decision) { if (decision.Label.HasValue) { return decision.Label.Value; } strategy.PlanCode(decision); decision.Label = labelGen++; return decision.Label.Value; }
private void GenerateCodeOrJump(Decision decision) { if (!strategy.TryInlineCode(decision)) { output.Append("goto ").Append(GetLabelText(decision)).AppendLine(); } }
private string GetLabelText(Decision node) { return FormatLabel(GetLabel(node)); }
private Decision Build( int first, int last, KeyValuePair <int, int>[] upperBounds) { int size = last - first; if (size > platform.MaxLinearCount) { // binary search nodes int middle = first + (size - 1) / 2; var branch = new RelationalBranchDecision( RelationalOperator.LessOrEqual, upperBounds[middle].Key); // positive branch branch.Left = Build(first, middle + 1, upperBounds); // negative branch branch.Right = Build(middle + 1, last, upperBounds); return(branch); } else { Decision result = null; RelationalBranchDecision lastBranch = null; // linear search nodes for (; first != last; ++first) { int key = upperBounds[first].Key; RelationalBranchDecision branch; if (first > 0 && (key - upperBounds[first - 1].Key) == 1) { branch = new RelationalBranchDecision(RelationalOperator.Equal, key); } else { branch = new RelationalBranchDecision(RelationalOperator.LessOrEqual, key); } branch.Left = new ActionDecision(upperBounds[first].Value); branch.Right = null; if (lastBranch != null) { lastBranch.Right = branch; } else { result = branch; } lastBranch = branch; } if (lastBranch != null) { lastBranch.Right = new ActionDecision(defaultAction); } else { result = new ActionDecision(defaultAction); } return(result); } }
private bool TryBuildElementaryTree(IIntMap<int> map, out Decision result) { result = null; int count = 0; foreach (var arrow in map.Enumerate()) { if (arrow.Value == map.DefaultValue) { continue; } ++count; if (count > platform.MaxLinearCount || arrow.Key.LongSize != 1) { return false; } } RelationalBranchDecision lastParent = null; foreach (var arrow in map.Enumerate()) { if (arrow.Value == map.DefaultValue) { continue; } var node = new RelationalBranchDecision(RelationalOperator.Equal, arrow.Key.First); node.Left = GetActionDecision(arrow.Value); if (lastParent == null) { result = node; } else { lastParent.Right = node; } lastParent = node; } lastParent.Right = DefaultActionDecision; return true; }