Reputation: 587
I've just started learning SML and I want to write a program which takes 2 int and a list of tuples, makes changes on them and then returns a list(BOXES is a list). List always has 2 tuples. In some if conditions I need to change the amount of an element in a tuple. So for example I define Xb1 and I gave it the amount of first element of the tuple ( #1 head ) and later I change the amount of Xb1 in the code(and return the list). But the problem is that this amount isn't changed. Here is the code:
fun MoveBoxL(Xw,Yw,boxes:(int * int)list) : BOXES =
let
val head = List.hd boxes
val tail = List.hd boxes
val Xb1= #1(head)
val Yb1 = #2(head)
val Xb2 = #1(tail)
val Yb2 = #2(tail)
in
if Yw=1 then boxes
else if head=(Xw,1) andalso Yw=2 then boxes
else if tail=(Xw,1) andalso Yw=2 then boxes
else if Yw=3 andalso head=(Xw,1) andalso tail=(Xw,2) then boxes
else if Yw=3 andalso tail=(Xw,1) andalso head=(Xw,2) then boxes
else if head=(Xw, Yw-2) andalso tail=(Xw, Yw-1) then (Yb1=Yb1-1 ; Yb2=Yb2-1 ; boxes)
else if head=(Xw, Yw-1) andalso tail=(Xw, Yw-2) then (Yb2=Yb2-1 ; Yb1=Yb1-1 ; boxes)
else if head=(Xw,Yw-1) then (Yb1=Yb1-1 ; boxes)
else if tail=(Xw,Yw-1) then (Yb2=Yb2-1 ; boxes)
else boxes
end;
cpn tools picture what's wrong?
Upvotes: 1
Views: 905
Reputation: 52008
I'm still not 100% sure what these rules for moving boxes are, but the following seems to capture your intent:
fun MoveBoxL(Xw,Yw,boxes:(int * int)list) =
let
val [box1,box2] = boxes
val (Xb1,Yb1) = box1
val (Xb2,Yb2) = box2
in
if Yw = 1 then boxes
else if box1=(Xw,1) andalso Yw=2 then boxes
else if box2=(Xw,1) andalso Yw=2 then boxes
else if Yw=3 andalso box1=(Xw,1) andalso box2=(Xw,2) then boxes
else if Yw=3 andalso box2=(Xw,1) andalso box1=(Xw,2) then boxes
else if box1=(Xw, Yw-2) andalso box2=(Xw, Yw-1) then [(Xb1,Yb1-1),(Xb2,Yb2-1)]
else if box1=(Xw, Yw-1) andalso box2=(Xw, Yw-2) then [(Xb1,Yb1-1),(Xb2,Yb2-1)]
else if box1=(Xw,Yw-1) then [(Xb1,Yb1-1),box2]
else if box2=(Xw,Yw-1) then [box1,(Xb2,Yb2-1)]
else boxes
end;
I renamed your head
and tail
to be box1
and box2
respectively. (and fixed a bug of yours where you were giving the wrong value to tail
) and used pattern matching to make the bindings easier to understand. More importantly, I replaced
(Yb1=Yb1-1 ; Yb2=Yb2-1 ; boxes)
by
[(Xb1,Yb1-1),(Xb2,Yb2-1)]
which is what I meant in the comments when I said that you should directly return what you want the new value to be.
It seems that the logic can be cleaned up by combining the clauses with have the same return value into single conditions using orelse
.
Upvotes: 1