CS 641 meeting -*- Outline -*- * developing loopless programs (Cohen's chapter 7) idea: use calculation to solve for programs ** overview ------------- CALCULATION OF PROGRAMS Given: specification Use: def. of weakest preconditions to calculate S For assignments: calculate expressions if-statements: calculate guards etc. ------------- one aspect of creativity/experience is what statement to use when we'll focus on these in this part, loops later ** calculating expressions in assignments (7.1) ------------------- EXAMPLE (CALC. EXPR. IN ASSIGNMENT) spec: var x:int ; x: x = 4 ------------------- this tells us we have to assign to x, so... ------------------- solve for E in: {true} x := E {x = 4} = true ==> wp.(x:=E).(x=4) = wp.(x:=E).(x=4) = (E = 4) -------------------- so x := 4 does the trick since the first step is always the same, we'll leave it out ----------------------- ANOTHER EXAMPLE spec: var q,r,x,y: int {0 <= x /\ 0 < y} ; q,r: 0 <= r /\ q*y + r = x /\ r=x solve for E,F, assuming 0 <= x /\ 0 < y: wp(q,r:=E,F).(0 <= r /\ q*y + r = x /\ r=x) = 0 <= F /\ E*y + F = x /\ F=x = 0 <= x /\ E*y + x = x /\ x=x = E*y + x = x = (E*y = 0) = 0, so ~(0=y)> (E = 0) --------------------- so E=0, and F=x desired assignment is q,r := 0,x used assumptions, so this show the implication of the wp by the assumptions, which is what was desired. can make choices along the way for the unknowns, as for F. sometimes the unknowns will pop out, as with E, or could have said to truthify it, choose E = 0, but that doesn't show the real reason for choosing E = 0. Summary: to determine an unknown expression in an assignment, calculate. ** developing IFs (7.2) Recall Thm (IF-Theorem): {Q} IF {R} equiv (Q ==> BB) /\ (all i : 0<=i S.0 [] B.1 -> S.1 ... [] B.(n-1) -> S.(n-1) fi and BB = (exists i : 0<=i BB (b) {Q /\ B.i} S.i {R} Heuristic: (1) develop guarded commands, B.i -> S.i, so that {Q /\ B.i} S.i {R} (2) stop when Q ==> (exists i:0<=i y = (x max y) = y >= x so G = (y >= x) but true ==> y >= x is not valid so need more guards... solve for G' in: {true /\ G'} m := x {m = (x max y)} --------------------- Q: can you solve for this G'? get x >= y. Q: do we have enough guards now? yes. Why? So the entire IF is if y >= x -> m := y [] x >= y -> m := x fi and we have a proof that {true} if y >= x -> m := y [] x >= y -> m := x fi {m = (x max y)} Compare to Cohen's spec: var x,y: int {x=X /\ y=Y} ; x : x = (X max Y) ** strengthening guards, restricting nondeterminism. for building an IF we assemble programs of the form {Q /\ B.i} S.i {R} into an IF, using the B.i as guards. You can always strengthen guards, because {X} S {Y} ==> {X /\ Z} S {Y} Q: does this mean that X ==> X /\ Z is valid? Your only constraint is that Q ==> BB still has to hold. For example because {y >= x} m := y {m = (x max y)}, we have {y >= x /\ ~(y=x)} m := y {m = (x max y)} = {y > x} m := y {m = (x max y)} Q: What else would have to be checked to use y > x in a guard? This kind of thing allows us to resrict or eliminate nondeterminism. if y > x -> m := y [] x >= y -> m := x fi and we have a proof that {true} if y > x -> m := y [] x >= y -> m := x fi {m = (x max y)} Q: Why restrict nondetreminism? to deal with if-then-else in other languages, efficiency considerations (and termination considerations in loops) ** discussion Q: What is the role of creativity/experience here?