1  class Orientation {
   2      public enum Direction {N, S, E, W}
   3  
   4      public Orientation(Direction d) {facing_ = d;}
   5  
   6      public Direction getDirection() {return facing_;}
   7  
   8      public void turnLeft() {
   9          switch (facing_) {
  10              case Direction.N: facing_ = Direction.W; break;
  11              case Direction.W: facing_ = Direction.S; break;
  12              case Direction.S: facing_ = Direction.E; break;
  13              case Direction.E: facing_ = Direction.N; break;
  14              }
  15          }
  16  
  17      public void turnRight() {
  18          switch (facing_) {
  19              case Direction.N: facing_ = Direction.E; break;
  20              case Direction.E: facing_ = Direction.S; break;
  21              case Direction.S: facing_ = Direction.W; break;
  22              case Direction.W: facing_ = Direction.N; break;
  23              }
  24          }
  25  
  26      // ======= Data Members ========
  27      private Direction facing_;
  28  }
  29  
  30  class Position {
  31      public Position(int x, int y, Action a) {
  32          x_ = x;
  33          y_ = y;
  34          a_ = a;
  35          }
  36  
  37      public void walk(Orientation o) {
  38          switch (o.getDirection()) {  
  39              case Orientation.Direction.N: ++y_; a_.performN(x_, y_); break;
  40              case Orientation.Direction.S: --y_; a_.performS(x_, y_); break;
  41              case Orientation.Direction.E: ++x_; a_.performE(x_, y_); break;
  42              case Orientation.Direction.W: --x_; a_.performW(x_, y_); break;
  43              }        
  44          }
  45  
  46      // ======= Data Members ========
  47      public int x_ {get; set;}
  48      public int y_ {get; set;}
  49      private Action a_;
  50  }
  51  
  52  class StateException : System.Exception
  53  {
  54      public StateException(char c) : base("Invalid input character '" + c + "'") { }
  55  }
  56  
  57  class Explorer {
  58      public Explorer(Orientation o, Position p) {
  59          orientation_ = o;
  60          position_    = p;
  61          }
  62  
  63      public Orientation getOrientation() {return orientation_;}
  64  
  65      public void turnBackwards() {orientation_.turnRight(); orientation_.turnRight();}
  66  
  67      public void processInput(string s) {foreach( char c in s) processInput(c);}
  68  
  69      private void processInput(char c) {
  70          switch(c) {
  71              case 'L': orientation_.turnLeft();      break;
  72              case 'R': orientation_.turnRight();     break;
  73              case 'W': position_.walk(orientation_); break;
  74              default: throw new StateException(c);
  75              }
  76          }
  77  
  78      // ======= Data Members ========
  79      private Orientation orientation_;
  80      private Position    position_;
  81  }
  82