- make-stateful-graph-agent startprocedure
Make a graph-traversal agent that models the graph and searches it thoroughly, stopping when the world is clean.
The agent can detect cycles.
- start
- Starting position of the agent (see `random-start')
(define (make-stateful-graph-agent start) (make-reflex-agent start (let ((world (make-hash-table)) (nodes (list->stack (list start))) (moves (make-stack))) (lambda (node clean?) (if (stack-empty? nodes) 'noop (if (not clean?) 'suck (let ((location (hash-table-ref/default world node (make-unknown-location clean?)))) (if (stack-empty? moves) (hash-table-set! world node location) (let ((last-move (stack-peek moves))) (if (eq? last-move 'backtrack) (stack-pop! moves) (if (eq? (stack-peek nodes) node) (let ((last-move (stack-pop! moves))) (vector-set! (location-neighbors location) (move->direction last-move) no-passage)) (let* ((last-node (stack-peek nodes)) (last-location (hash-table-ref world last-node))) (if (hash-table-exists? world node) (stack-push! nodes cycle) (begin (hash-table-set! world node location) (stack-push! nodes node))) (vector-set! (location-neighbors location) (move->direction (reverse-move last-move)) last-node) (vector-set! (location-neighbors last-location) (move->direction last-move) node)))))) (let ((new-moves (map direction->move (undiscovered-directions location)))) (if (or (cycle? (stack-peek nodes)) (null? new-moves)) (begin (stack-pop! nodes) (if (stack-empty? moves) 'noop (let ((move (stack-pop! moves))) (stack-push! moves 'backtrack) (reverse-move move)))) (let ((move (list-ref new-moves (bsd-random (length new-moves))))) (stack-push! moves move) move))))))))))