sw-examples: smarter-prolog-monkey-solver.sw3

Raw file here.
-- Try to solve the monkey banana problem
-- In this version, we try to solve the problem a little smarter than brute force
-- load prolog-monkey.sw3 before you load this file.

-- updated to the version 3.1.1 language


set-up-initial-state
the |objects> => rel-kets[at]
the |locations> => at rel-kets[at]
the-list-of |operators> => |op: get-go-details> + |op: get-push-details> + |op: get-climb-on-details> + |op: get-grab-details>
not |yes> => |no>
not |no> => |yes>

reset |*> #=>
    unlearn[*] starts-with |depth: >
    current |depth> => |depth: 0>
    unlearn[the] |plan>
    unlearn[the-used] |operators>
    set-up-initial-state
    |>

save-state |*> #=>
    previous-on |monkey> => |floor>
    previous-on |box> => |floor>
    previous-at |monkey> => |a>
    previous-at |box> => |b>
    previous-at |bananas> => |c>
    previous-status |bananas> => |hanging>
    |state saved>

restore-state |*> #=>
    on |monkey> => previous-on |monkey>
    on |box> => previous-on |box>
    at |monkey> => previous-at |monkey>
    at |box> => previous-at |box>
    at |bananas> => previous-at |bananas>
    status |bananas> => previous-status |bananas>
    |state restored>

depth-back-track |*> #=>
    unlearn[failed-attempts] current |depth>
    current |depth> => minus[1] current |depth>
    |depth back track>


display-details (*) #=>
    extract-value sselect[1,1] |__self> _ |(> _ smerge[", "] sselect[2, -1] |__self> _ |)>

comma-merge (*,*) #=> |__self1> _ |, > _ |__self2>


get-go-details |*> #=>
    unlearn[move] |to>
    move |to> => pick-elt drop (the |locations> - at |monkey> - attempted-go-move current |depth>)
    attempted-go-move current |depth> +=> move |to>
    the |details> => |op: go> . |> . at |monkey> . move |to>
    value-if( do-you-know move |to>, the |details>, |> )

get-push-details |*> #=>
    unlearn[the] (|choices> + |choice>)
    the |choices> => drop op-for( |op: comma-merge>, the |objects> -1 |monkey>, the |locations> -1 at |monkey>)
    the |choice> => pick-elt drop (the |choices> -1 attempted-push-choice current |depth>)
    the |object> => sselect[1,1] ssplit[", "] the |choice>
    move |to> => sselect[2,2] ssplit[", "] the |choice>
    attempted-push-choice current |depth> +=> the |choice>
    the |details> => |op: push> . |> . the |object> . at |monkey> . move |to>
    value-if( do-you-know the |choice>, the |details>, |> )

get-climb-on-details |*> #=>
    unlearn[climb] |object>
    climb |object> => pick-elt drop (the |objects> -1 |monkey> -1 attempted-climb-on-object current |depth>)
    attempted-climb-on-object current |depth> +=> climb |object>
    the |details> => |op: climb-on> . |> . climb |object>
    value-if( do-you-know climb |object>, the |details>, |> )

get-grab-details |*> #=>
    unlearn[the-grab] |object>
    the-grab |object> => pick-elt drop (the |objects> -1 |monkey> -1 attempted-grab-object current |depth>)
    attempted-grab-object current |depth> +=> the-grab |object>
    the |details> => |op: grab> . |> . the-grab |object>
    value-if( do-you-know the-grab |object>, the |details>, |> )


solve-v1 |*> #=>
    reset
    try-operator-v1

try-operator-v1 (*) #=>
    unlearn[the-solution] (|operator> + |details> + |result>)
    the-solution |operator> => pick-elt drop (the-list-of |operators> -1 the-used |operators> -1 the-tried-operators current |depth>)
    the-solution |details> => apply(the-solution |operator>, |>)
    the-solution |result> => compile the-solution |details>
    op-if( or( not do-you-know the-solution |details>, has-prefix["monkey failed to "] the-solution |result>), |op: monkey-failed-v1>, |op: monkey-succeeded-v1>)

monkey-failed-v1 (*) #=>
    print |monkey failed at something>
    the-tried-operators current |depth> +=> value-if( do-you-know the-solution |details>, |>, the-solution |operator>)
    op-if( do-you-know the-solution |operator>, |op: try-operator-v1>, |op: no-operators-left-v1>)
    |>

-- Currently if we run out of operators we reset back to the starting state
-- It would be nice if we could instead back-track, instead of a full reset.
no-operators-left-v1 (*) #=>
    print |no operators left, resetting ... >
    reset
    try-operator-v1
    |>

monkey-succeeded-v1 (*) #=>
    print |monkey succeeded at something>
    the |plan> .=> display-details the-solution |details>
    the-used |operators> +=> the-solution |operator>
    current |depth> => plus[1] current |depth>
    the-current |state> => test-for-goal-state |>
    print (|The current state:> __ the-current |state> . | >)
    op-if( the-current |state> == |reached goal state!>, |op: finished-v1>, |op: try-operator-v1>)

finished-v1 (*) #=>
    print (|The plan:> __ smerge[" "] the |plan>)
    |>


-- now solve it:
-- solve-v1

------------------------------------------------------------------------------
-- the version 3.1.1 solve code:

solve |*> #=>
    reset
    try-operator

try-operator (*) #=>
    unlearn[the-solution] (|operator> + |details> + |result>)
    the-solution |operator> => pick-elt drop (the-list-of |operators> -1 the-used |operators> -1 the-tried-operators current |depth>)
    the-solution |details> => apply(the-solution |operator>, |>)
    the-solution |result> => compile the-solution |details>
    if( or( not do-you-know the-solution |details>, has-prefix["monkey failed to "] the-solution |result> )):
        print |monkey failed at something>
        the-tried-operators current |depth> +=> value-if( do-you-know the-solution |details>, |>, the-solution |operator>)
        if( do-you-know the-solution |operator> ):
            try-operator
        else:
            print |no operators left, resetting ... >
            reset
            try-operator
        end:
    else:
        print |monkey succeeded at something>
        the |plan> .=> display-details the-solution |details>
        the-used |operators> +=> the-solution |operator>
        current |depth> => plus[1] current |depth>
        the-current |state> => test-for-goal-state |>
        print (|The current state:> __ the-current |state> . | >)
        if( the-current |state> == |reached goal state!> ):
            print (|The plan:> __ smerge[" "] the |plan>)
        else:
            try-operator
        end:
    end:
    |>

-- now solve it:
solve

Home