Guest User

Untitled

a guest
Jan 31st, 2015
222
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1.  
  2. enum ExecutionState
  3. {
  4.     S_EVAL,
  5.     S_CALL1,
  6.     S_CALL2
  7. };
  8.  
  9. enum NodeType
  10. {
  11.     AND_OPERATOR,
  12.     OR_OPERATOR,
  13.     VALUE  
  14. };
  15.  
  16. class LocalVars
  17. {
  18.     public IEnumerator<Node> Enumerator;
  19.     public bool Result;
  20. }
  21.  
  22. class Context
  23. {
  24.     public Node Node;      
  25.     public LocalVars LocalVariables;       
  26.     public ExecutionState State;
  27.    
  28.     public Context(Node node, ExecutionState state)
  29.     {
  30.         this.Node = node;
  31.         this.State = state;
  32.         this.LocalVariables = new LocalVars();
  33.     }
  34. };
  35.  
  36. class Node
  37. {
  38.     public bool Value;         
  39.     public NodeType Type;
  40.     public List<Node> Childrens;
  41. };
  42.  
  43. static bool EvaluateNode(Node node)
  44. {
  45.     Stack<Context> stack = new Stack<Context>();
  46.     Context context = new Context(node, ExecutionState.S_EVAL);            
  47.     stack.Push(context);
  48.    
  49.     bool returnresult = false;
  50.     while(stack.Any())
  51.     {
  52.         context = stack.Pop();
  53.         switch(context.State)
  54.         {
  55.             case ExecutionState.S_EVAL:
  56.                 switch(context.Node.Type)
  57.                 {
  58.                     case NodeType.AND_OPERATOR:
  59.                         if(context.LocalVariables.Enumerator == null)
  60.                         {
  61.                             context.LocalVariables.Enumerator = context.Node.Childrens.GetEnumerator();
  62.                             context.LocalVariables.Result = true;
  63.                         }
  64.                        
  65.                         if(context.LocalVariables.Enumerator.MoveNext())
  66.                         {
  67.                             context.State = ExecutionState.S_CALL1;
  68.                             stack.Push(context);            // push resume with S_CALL1
  69.                                                                
  70.                             Context call = new Context(context.LocalVariables.Enumerator.Current, ExecutionState.S_EVAL);                                                  
  71.                             stack.Push(call);           // push call
  72.                         }
  73.                         else
  74.                         {
  75.                             returnresult = context.LocalVariables.Result;    // no push -> return
  76.                         }
  77.                         break;
  78.                        
  79.                     case NodeType.OR_OPERATOR:
  80.                         if(context.LocalVariables.Enumerator == null)
  81.                         {
  82.                             context.LocalVariables.Enumerator = context.Node.Childrens.GetEnumerator();
  83.                             context.LocalVariables.Result = false;
  84.                         }
  85.                        
  86.                         if(context.LocalVariables.Enumerator.MoveNext())
  87.                         {
  88.                             context.State = ExecutionState.S_CALL2;
  89.                             stack.Push(context);            // push resume with S_CALL2
  90.                            
  91.                             Context call = new Context(context.LocalVariables.Enumerator.Current, ExecutionState.S_EVAL);                                                  
  92.                             stack.Push(call);           // push call
  93.                         }
  94.                         else
  95.                         {
  96.                             returnresult = context.LocalVariables.Result;    // no push -> return
  97.                         }
  98.                         break;
  99.                        
  100.                     case NodeType.VALUE:
  101.                         returnresult = context.Node.Value;  // no push -> return
  102.                         break;
  103.                 }
  104.                 break;
  105.                
  106.             case ExecutionState.S_CALL1:
  107.                 context.LocalVariables.Result = context.LocalVariables.Result && returnresult;
  108.                 context.State = ExecutionState.S_EVAL;
  109.                 stack.Push(context);                        // continue with S_EVAL
  110.                 break;
  111.                
  112.             case ExecutionState.S_CALL2:
  113.                 context.LocalVariables.Result = context.LocalVariables.Result || returnresult;
  114.                 context.State = ExecutionState.S_EVAL;
  115.                 stack.Push(context);                        // continue with S_EVAL
  116.                 break;
  117.         }
  118.     }
  119.    
  120.     return returnresult;
  121. }
RAW Paste Data