%% s_morphing_vehicles.sp -- SPARC version %% Last Modified: 3/16/14 %% Additional Exercise for Chapter 8 %% Recall the vehicle hierarchy from Section 5.4.2 in which we had a %% vehicle, Darling, that could be both a sub and a car. %% In this problem, instead of simply belonging to two categories at %% once, the vehicle morphs from one mode into another; hence, the %% properties inherited by Darling are fluents. %% %% --------- %% Exercise: %% --------- %% Consider an action "morph" turning an object from a car to a sub, etc. %% For simplicity, assume that an object can only belong to one class %% at a time and that morphing only occurs between leaf classes. %% Describe the following vehicle hierarchy and action morph in SPARC. %% %% vehicle %% / | \ %% land_vehicle sea_vehicle air_vehicle %% | | | %% car sub plane %% %% Initially, Darling is a car and the Narwhal is a sub. %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% #const n = 1. %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% sorts #vehicle_mode = {sub, car, plane}. #class = #vehicle_mode + {land_vehicle, sea_vehicle, air_vehicle, vehicle}. #object = {narwhal, darling}. #step = 0..n. #inertial_fluent = is_a(#object,#class). #defined_fluent = member(#object,#class). #fluent = #inertial_fluent + #defined_fluent. #action = morph(#object,#vehicle_mode). %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% predicates is_subclass(#class,#class). subclass(#class,#class). holds(#fluent,#step). occurs(#action,#step). %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% rules % Description of subclass links: is_subclass(sub,sea_vehicle). is_subclass(car,land_vehicle). is_subclass(plane,air_vehicle). is_subclass(air_vehicle,vehicle). is_subclass(sea_vehicle,vehicle). is_subclass(land_vehicle,vehicle). %% Subclass Relation: subclass(C1,C2) :- is_subclass(C1,C2). subclass(C1,C2) :- is_subclass(C1,C3), subclass(C3,C2). -subclass(C1,C2) :- not subclass(C1,C2). %% Laws: % morph(O,C) causes is_a(O,C) holds(is_a(O,C),I2) :- occurs(morph(O,C),I1), I2 = I1 + 1. % -is_a(O,C2) if is_a(O,C1), C1 != C2 -holds(is_a(O,C2),I) :- holds(is_a(O,C1),I), C1 != C2. % member(X,C) if is_a(X,C) holds(member(X,C),I) :- holds(is_a(X,C),I). % member(X,C) if is_a(X,C0), subclass(C0,C) holds(member(X,C),I) :- holds(is_a(X,C0),I), subclass(C0,C). %% Inertia Axioms: holds(F,I2) :- #inertial_fluent(F), holds(F,I1), not -holds(F,I2), I2 = I1 + 1. -holds(F,I2) :- #inertial_fluent(F), -holds(F,I1), not holds(F,I2), I2 = I1 + 1. %% CWA for Defined Fluents: -holds(F,I) :- #defined_fluent(F), not holds(F,I). %% CWA for Actions -occurs(A,I) :- not occurs(A,I). %% Initial State: holds(is_a(narwhal,sub),0). holds(is_a(darling, car),0). occurs(morph(darling,sub),0).