CPSC 322 - Lecture 31 - November 19, 2004

CPSC 322 - Lecture 31

Planning and Action


I.  Planning and search

Everything we've seen so far (and everything we will see,
for that matter) can be characterized as search.  But as
the kinds of problems being solved get bigger, the nature
of the solution changes:  the knowledge required to do the
job increases dramatically, the operators become more 
complex, and the representation schemes are mixed together.

If we add to all that the notion that there's an intelligent
agent (e.g., a robot) acting in and making changes to the
world...especially if we add the possibility that the agent's
actions might be irrevocable, expensive, and maybe even 
fatal...then solutions to problems like this are often given 
the more specific name of "planning" instead of search.   The
name "planning" indicates a desire on the part of the agent
to compute several, if not all, the steps of a problem-
solving procedure before executing any of them.

Planning requires lots of knowledge, especially about
the operators that are available to the agent.  To do
planning well, the agent also needs comprehensive knowledge
of the problem domain in advance...a map of the terrain,
if you will.  The need to have voluminous knowledge of 
the domain leads to a fundamental issue in planning: the
frame problem.

The frame problem is essentially this:  given that the
agent may move about in the domain and change things
within the domain, how can we keep track of what changes
and, more importantly, what doesn't change in the domain
as time goes by?  If you have an artificially small domain,
like the tile puzzle, then the solution is simple:  just
make a copy of the entire domain with the changes explicitly
shown.  But if your domain is Meridiani Planum on Mars or
150 miles of dirt path in the Southern California desert,
making copies of everything you know about the domain just
to reflect relatively tiny changes can be very very 
expensive.


II.  The STRIPS solution

One elegant solution to the frame problem was put forward
back in the early 1970s in a program called STRIPS (STanford
Research Institute Problem Solver).  STRIPS was the planning
software for the robot known as Shakey...you saw Shakey
in the AI documentary.  Shakey was the robot that "thought"
for 15 minutes before moving one meter.

STRIPS had an internal model of where it was in its world 
(the initial state) and knowledge of where it wanted to be
(the goal state), and it found a sequence of operators
(a plan) to get it from the initial state to the goal.

So far, that's not exactly novel.  What's novel is how
STRIPS represented the intermediate states.  Instead of
making a copy of the previous state with changes
explicitly represented, STRIPS subsequent states as the
sequence of actions that would get it from the initial
state to the state in question.  To facilitate this, each
operator in STRIPS carried with it the following information:

preconditions:  what must be true about the state of the
     world to use the operator

add list:  what becomes true about the world when the
     operator is applied

delete list:  what is no longer true when the operator
     is applied

In the PowerPoint slides we walk through an example of
how STRIPS solves an extremely simple problem in the
blocks world domain.  The example shows, step by step,
how the simple STRIPS planner written in CILOG (Chapter
8.3, page 302) works when trying to stack one block on
top of another.  Here's the actual code after I tweaked
it a bit:

/* 
This is an implementation of the simple STRIPS planner
shown on page 302 of the Computational Intelligence text.
The domain is a very simple blocks world problem, and 
the representations of state and actions, while described
in chapter 8 of the text, are adapted from a more 
complicated sample program and knowledge base found at
http://www.cs.ubc.ca/spider/poole/ci/code/cilog/cilog_code/cilog_code.html
(click on delrob_strips.pl).

launch it with the query:
cilog: ask goals(G) & achieve_all(G,init,Plan).

Note that the add list is denoted here by "achieves" instead 
of "add", and that the add and delete lists aren't exactly 
lists.
*/

/* stack action */
preconditions(stack(X,Y),[cleartop(Y),holding(X)]).
achieves(stack(X,Y),armempty).
achieves(stack(X,Y),on(X,Y)).
deletes(stack(X,Y),cleartop(Y)).
deletes(stack(X,Y),holding(X)).

/* unstack action */
preconditions(unstack(X,Y),[on(X,Y),cleartop(X),armempty]).
achieves(unstack(X,Y),holding(X)).
achieves(unstack(X,Y),cleartop(Y)).
deletes(unstack(X,Y),on(X,Y)).
deletes(unstack(X,Y),armempty).

/* pickup action */
preconditions(pickup(X),[cleartop(X),ontable(X),armempty]).
achieves(pickup(X),holding(X)).
deletes(pickup(X),ontable(X)).
deletes(pickup(X),armempty).

/* putdown action */
preconditions(putdown(X),[holding(X)]).
achieves(putdown(X),ontable(X)).
achieves(putdown(X),armempty).
deletes(putdown(X),holding(X)).


/* initial situation */

holds(ontable(a),init).
holds(ontable(b),init).
holds(cleartop(a),init).
holds(cleartop(b),init).
holds(armempty,init).
holds(ontable(c),init).
holds(cleartop(c),init).

achieves(init,X) <- holds(X,init).

goals([ontable(b),cleartop(a),armempty,on(a,b)]).

/* the simple STRIPS planner */

remove(X,[X|Y],Y).

achieve_all([],W0,W0).

achieve_all(Goals,W0,W2) <- 
     remove(G,Goals,Rem_Gs) &
     achieve(G,W0,W1) &
     achieve_all(Rem_Gs,W1,W2).

achieve(G,W,W) <- holds(G,W).

achieve(G,W0,do(Action,W1)) <-
     achieves(Action,G) &
     preconditions(Action,Pre) &
     achieve_all(Pre,W0,W1).

Last revised: December 7, 2004