Subversion Repositories programming

Rev

Go to most recent revision | Blame | Compare with Previous | Last modification | View Log | RSS feed

#!/usr/bin/env python

__author__    = "Ira W. Snyder (devel@irasnyder.com)"
__copyright__ = "Copyright (c) 2006, Ira W. Snyder (devel@irasnyder.com)"
__license__   = "GNU GPL v2 (or, at your option, any later version)"

from PyCompat import *
import re

# Solution to the Monkey and Banana Problem

class Action (object):
        def __init__ (self, State):
                self.State = State
                self.PC = []
                self.AL = []
                self.DL = []

        def __repr__ (self):
                return '%s' % self.State

        def meetsPreconditions (self):
                for e in self.PC:
                        if e not in self.State:
                                return False

                return True

        def takeAction (self):
                if not self.meetsPreconditions ():
                        raise ValueError

                for e in self.AL:
                        self.State.add (e)

                for e in self.DL:
                        self.State.remove (e)

                # Return the new State
                return self.State

        def isGoal (self):
                return 'HasBanana()' in self.State

        def findMonkeyPosition (self):
                regex = re.compile ('At\(Monkey,(.+)\)')

                for e in self.State:
                        if regex.match (e):
                                return regex.match (e).group (1)

        def findBoxPosition (self):
                regex = re.compile ('At\(Box,(.+)\)')

                for e in self.State:
                        if regex.match (e):
                                return regex.match (e).group (1)

        def monkeyOnBox (self):
                return 'OnBox()' in self.State


class Walk (Action):
        (DOOR, WINDOW, MIDDLE) = ('Door', 'Window', 'Middle')

        def __init__ (self, State, F, T):
                Action.__init__ (self, State)
                self.F = F
                self.T = T

                self.PC = ['At(Monkey,%s)' % (F,) , 'OnFloor()']
                self.AL = ['At(Monkey,%s)' % (T,)]
                self.DL = ['At(Monkey,%s)' % (F,)]

class Push (Action):
        (DOOR, WINDOW, MIDDLE) = ('Door', 'Window', 'Middle')

        def __init__ (self, State, F, T):
                Action.__init__ (self, State)
                self.F = F
                self.T = T

                self.PC = ['At(Monkey,%s)' % (F,) , 'At(Box,%s)' % (F,) , 'OnFloor()']
                self.AL = ['At(Monkey,%s)' % (T,) , 'At(Box,%s)' % (T,)]
                self.DL = ['At(Monkey,%s)' % (F,) , 'At(Box,%s)' % (F,)]

class Climb (Action):
        (UP, DOWN) = ('Up', 'Down')

        def __init__ (self, State, D):
                Action.__init__ (self, State)
                self.D = D

                if D == self.UP:
                        self.PC = ['At(Monkey,%s)' % (self.findBoxPosition()), \
                                                'At(Box,%s)' % (self.findMonkeyPosition()), 'OnFloor()']
                        self.AL = ['OnBox()']
                        self.DL = ['OnFloor()']
                else: # D == DOWN
                        self.PC = ['At(Monkey,%s)' % (self.findBoxPosition()), \
                                                'At(Box,%s)' % (self.findMonkeyPosition()), 'OnBox()']
                        self.AL = ['OnFloor()']
                        self.DL = ['OnBox()']

class Grab (Action):
        (DOOR, WINDOW, MIDDLE) = ('Door', 'Window', 'Middle')

        def __init__ (self, State):
                Action.__init__ (self, State)
                self.PC = ['OnBox()', 'At(Monkey,%s)' % (self.MIDDLE), 'NoBanana()']
                self.AL = ['HasBanana()']
                self.DL = ['NoBanana()']

# vim: set ts=4 sts=4 sw=4: