36
36
isnumber , issequence , Expr , expr , subexpressions
37
37
)
38
38
import agents
39
+ from search import astar_search , PlanRoute
39
40
40
41
import itertools
41
42
import random
@@ -763,7 +764,7 @@ def location(x, y, time = None):
763
764
def implies (lhs , rhs ):
764
765
return Expr ('==>' , lhs , rhs )
765
766
766
- def implies_and_implies (lhs , rhs ):
767
+ def equiv (lhs , rhs ):
767
768
return Expr ('<=>' , lhs , rhs )
768
769
769
770
# Helper Function
@@ -811,8 +812,8 @@ def __init__(self,dimrow):
811
812
pits_in .append (pit (x , y - 1 ))
812
813
wumpus_in .append (wumpus (x , y - 1 ))
813
814
814
- self .tell (implies_and_implies (breeze (x , y ), new_disjunction (pits_in )))
815
- self .tell (implies_and_implies (stench (x , y ), new_disjunction (wumpus_in )))
815
+ self .tell (equiv (breeze (x , y ), new_disjunction (pits_in )))
816
+ self .tell (equiv (stench (x , y ), new_disjunction (wumpus_in )))
816
817
817
818
818
819
## Rule that describes existence of at least one Wumpus
@@ -837,8 +838,8 @@ def __init__(self,dimrow):
837
838
self .tell (location (1 , 1 , 0 ))
838
839
for i in range (1 , dimrow + 1 ):
839
840
for j in range (1 , dimrow + 1 ):
840
- self .tell (implies (location (i , j , 0 ), implies_and_implies (percept_breeze (0 ), breeze (i , j ))))
841
- self .tell (implies (location (i , j , 0 ), implies_and_implies (percept_stench (0 ), stench (i , j ))))
841
+ self .tell (implies (location (i , j , 0 ), equiv (percept_breeze (0 ), breeze (i , j ))))
842
+ self .tell (implies (location (i , j , 0 ), equiv (percept_stench (0 ), stench (i , j ))))
842
843
if i != 1 or j != 1 :
843
844
self .tell (~ location (i , j , 0 ))
844
845
@@ -903,13 +904,13 @@ def add_temporal_sentences(self, time):
903
904
## current location rules
904
905
for i in range (1 , self .dimrow + 1 ):
905
906
for j in range (1 , self .dimrow + 1 ):
906
- self .tell (implies (location (i , j , time ), implies_and_implies (percept_breeze (time ), breeze (i , j ))))
907
- self .tell (implies (location (i , j , time ), implies_and_implies (percept_stench (time ), stench (i , j ))))
907
+ self .tell (implies (location (i , j , time ), equiv (percept_breeze (time ), breeze (i , j ))))
908
+ self .tell (implies (location (i , j , time ), equiv (percept_stench (time ), stench (i , j ))))
908
909
909
910
s = list ()
910
911
911
912
s .append (
912
- implies_and_implies (
913
+ equiv (
913
914
location (i , j , time ), location (i , j , time ) & ~ move_forward (time ) | percept_bump (time )))
914
915
915
916
if i != 1 :
@@ -929,72 +930,79 @@ def add_temporal_sentences(self, time):
929
930
930
931
## add sentence about safety of location i,j
931
932
self .tell (
932
- implies_and_implies (ok_to_move (i , j , time ), ~ pit (i , j ) & ~ wumpus (i , j ) & wumpus_alive (time ))
933
+ equiv (ok_to_move (i , j , time ), ~ pit (i , j ) & ~ wumpus (i , j ) & wumpus_alive (time ))
933
934
)
934
935
935
936
## Rules about current orientation
936
937
937
938
a = facing_north (t ) & turn_right (t )
938
939
b = facing_south (t ) & turn_left (t )
939
940
c = facing_east (t ) & ~ turn_left (t ) & ~ turn_right (t )
940
- s = implies_and_implies (facing_east (time ), a | b | c )
941
+ s = equiv (facing_east (time ), a | b | c )
941
942
self .tell (s )
942
943
943
944
a = facing_north (t ) & turn_left (t )
944
945
b = facing_south (t ) & turn_right (t )
945
946
c = facing_west (t ) & ~ turn_left (t ) & ~ turn_right (t )
946
- s = implies_and_implies (facing_west (time ), a | b | c )
947
+ s = equiv (facing_west (time ), a | b | c )
947
948
self .tell (s )
948
949
949
950
a = facing_east (t ) & turn_left (t )
950
951
b = facing_west (t ) & turn_right (t )
951
952
c = facing_north (t ) & ~ turn_left (t ) & ~ turn_right (t )
952
- s = implies_and_implies (facing_north (time ), a | b | c )
953
+ s = equiv (facing_north (time ), a | b | c )
953
954
self .tell (s )
954
955
955
956
a = facing_west (t ) & turn_left (t )
956
957
b = facing_east (t ) & turn_right (t )
957
958
c = facing_south (t ) & ~ turn_left (t ) & ~ turn_right (t )
958
- s = implies_and_implies (facing_south (time ), a | b | c )
959
+ s = equiv (facing_south (time ), a | b | c )
959
960
self .tell (s )
960
961
961
962
## Rules about last action
962
- self .tell (implies_and_implies (move_forward (t ), ~ turn_right (t ) & ~ turn_left (t )))
963
+ self .tell (equiv (move_forward (t ), ~ turn_right (t ) & ~ turn_left (t )))
963
964
964
965
##Rule about the arrow
965
- self .tell (implies_and_implies (have_arrow (time ), have_arrow (t ) & ~ shoot (t )))
966
+ self .tell (equiv (have_arrow (time ), have_arrow (t ) & ~ shoot (t )))
966
967
967
968
##Rule about Wumpus (dead or alive)
968
- self .tell (implies_and_implies (wumpus_alive (time ), wumpus_alive (t ) & ~ percept_scream (time )))
969
+ self .tell (equiv (wumpus_alive (time ), wumpus_alive (t ) & ~ percept_scream (time )))
969
970
970
971
971
972
def ask_if_true (self , query ):
972
973
return pl_resolution (self , query )
973
-
974
-
974
+
975
+
975
976
# ______________________________________________________________________________
976
977
977
978
978
979
class WumpusPosition ():
979
- def __init__ (self , X , Y , orientation ):
980
- self .X = X
981
- self .Y = Y
980
+ def __init__ (self , x , y , orientation ):
981
+ self .X = x
982
+ self .Y = y
982
983
self .orientation = orientation
983
984
984
985
985
986
def get_location (self ):
986
987
return self .X , self .Y
987
988
989
+ def set_location (self , x , y ):
990
+ self .X = x
991
+ self .Y = y
992
+
988
993
def get_orientation (self ):
989
994
return self .orientation
990
995
991
- def equals (self , wumpus_position ):
992
- if wumpus_position .get_location () == self .get_location () and \
993
- wumpus_position .get_orientation ()== self .get_orientation ():
996
+ def set_orientation (self , orientation ):
997
+ self .orientation = orientation
998
+
999
+ def __eq__ (self , other ):
1000
+ if other .get_location () == self .get_location () and \
1001
+ other .get_orientation ()== self .get_orientation ():
994
1002
return True
995
1003
else :
996
1004
return False
997
-
1005
+
998
1006
# ______________________________________________________________________________
999
1007
1000
1008
@@ -1041,9 +1049,8 @@ def execute(self, percept):
1041
1049
goals = list ()
1042
1050
goals .append ([1 , 1 ])
1043
1051
self .plan .append ('Grab' )
1044
- actions = plan_route (self .current_position ,goals ,safe_points )
1045
- for action in actions :
1046
- self .plan .append (action )
1052
+ actions = self .plan_route (self .current_position ,goals ,safe_points )
1053
+ self .plan .extend (actions )
1047
1054
self .plan .append ('Climb' )
1048
1055
1049
1056
if len (self .plan ) == 0 :
@@ -1059,9 +1066,8 @@ def execute(self, percept):
1059
1066
if u not in unvisited_and_safe and s == u :
1060
1067
unvisited_and_safe .append (u )
1061
1068
1062
- temp = plan_route (self .current_position ,unvisited_and_safe ,safe_points )
1063
- for t in temp :
1064
- self .plan .append (t )
1069
+ temp = self .plan_route (self .current_position ,unvisited_and_safe ,safe_points )
1070
+ self .plan .extend (temp )
1065
1071
1066
1072
if len (self .plan ) == 0 and self .kb .ask_if_true (have_arrow (self .t )):
1067
1073
possible_wumpus = list ()
@@ -1070,26 +1076,23 @@ def execute(self, percept):
1070
1076
if not self .kb .ask_if_true (wumpus (i , j )):
1071
1077
possible_wumpus .append ([i , j ])
1072
1078
1073
- temp = plan_shot (self .current_position , possible_wumpus , safe_points )
1074
- for t in temp :
1075
- self .plan .append (t )
1079
+ temp = self .plan_shot (self .current_position , possible_wumpus , safe_points )
1080
+ self .plan .extend (temp )
1076
1081
1077
1082
if len (self .plan ) == 0 :
1078
1083
not_unsafe = list ()
1079
1084
for i in range (1 , self .dimrow + 1 ):
1080
1085
for j in range (1 , self .dimrow + 1 ):
1081
1086
if not self .kb .ask_if_true (ok_to_move (i , j , self .t )):
1082
1087
not_unsafe .append ([i , j ])
1083
- temp = plan_route (self .current_position , not_unsafe , safe_points )
1084
- for t in temp :
1085
- self .plan .append (t )
1088
+ temp = self .plan_route (self .current_position , not_unsafe , safe_points )
1089
+ self .plan .extend (temp )
1086
1090
1087
1091
if len (self .plan ) == 0 :
1088
1092
start = list ()
1089
1093
start .append ([1 , 1 ])
1090
- temp = plan_route (self .current_position , start , safe_points )
1091
- for t in temp :
1092
- self .plan .append (t )
1094
+ temp = self .plan_route (self .current_position , start , safe_points )
1095
+ self .plan .extend (temp )
1093
1096
self .plan .append ('Climb' )
1094
1097
1095
1098
action = self .plan [0 ]
@@ -1100,12 +1103,37 @@ def execute(self, percept):
1100
1103
return action
1101
1104
1102
1105
1103
- def plan_route (current , goals , allowed ):
1104
- raise NotImplementedError
1106
+ def plan_route (self , current , goals , allowed ):
1107
+ problem = PlanRoute (current , goals , allowed , self .dimrow )
1108
+ return astar_search (problem ).solution ()
1109
+
1105
1110
1106
-
1107
- def plan_shot (current , goals , allowed ):
1108
- raise NotImplementedError
1111
+ def plan_shot (self , current , goals , allowed ):
1112
+ shooting_positions = set ()
1113
+
1114
+ for loc in goals :
1115
+ x = loc [0 ]
1116
+ y = loc [1 ]
1117
+ for i in range (1 , self .dimrow + 1 ):
1118
+ if i < x :
1119
+ shooting_positions .add (WumpusPosition (i , y , 'EAST' ))
1120
+ if i > x :
1121
+ shooting_positions .add (WumpusPosition (i , y , 'WEST' ))
1122
+ if i < y :
1123
+ shooting_positions .add (WumpusPosition (x , i , 'NORTH' ))
1124
+ if i > y :
1125
+ shooting_positions .add (WumpusPosition (x , i , 'SOUTH' ))
1126
+
1127
+ # Can't have a shooting position from any of the rooms the Wumpus could reside
1128
+ orientations = ['EAST' , 'WEST' , 'NORTH' , 'SOUTH' ]
1129
+ for loc in goals :
1130
+ for orientation in orientations :
1131
+ shooting_positions .remove (WumpusPosition (loc [0 ], loc [1 ], orientation ))
1132
+
1133
+ actions = list ()
1134
+ actions .extend (self .plan_route (current , shooting_positions , allowed ))
1135
+ actions .append ('Shoot' )
1136
+ return actions
1109
1137
1110
1138
1111
1139
# ______________________________________________________________________________
0 commit comments