Korrkthd af Algoritmr md fokus på whil-løkkr Kim Skak Larsn Institut for Matmatik og Datalogi Syddansk Univrsitt, Odns Sptmbr 2001 Introduktion Dnn not supplrr korrkthdsafsnittt i [1], som r dn anvndt lærbog i Algoritmr og Datastrukturr (DM02), ftrårt 2001. Korrkthd Vi fokusrr på korrkthd af algoritmr og programmr, dr forvnts at fortag n brgning og drftr stands. Dt ovrhovdt at stands blivr n dl af korrkthdskritrit. raditionlt brugs ordt trminring om dt at stands. For at adskill trminringsproblmatikkn fra rstn af korrkthdsargumntationn indførs bgrbt partil korrkthd, som dfinrs til at btyd, at n givn algoritm r korrkt (givr dt korrkt rsultat), hvis dn nogn sind trminrr. Drmd kan korrkthd dfinrs som følgr: 1
En algoritm r korrkt, hvis 1. algoritmn trminrr, og 2. algoritmn r partilt korrkt. Partil korrkthd Som i [1] basrs partil korrkthd på præ- og postbtinglsr som omsluttr n algoritm, hvor algoritm hr rfrrr til n vilkårlig brgning. Dvs. at n algoritm kan vær n komplicrt størrls llr dn kan vær ksmplvis n nklt if-sætning llr n tildling af n værdi til n variabl. En algoritm r partilt korrkt, hvis dr for nhvr udførls, for hvilkn præbtinglsn r opfyldt, gældr, at hvis postbtinglsn nås, så r dn også opfyldt. Hvis vi ladr Alg, og btgn hnholdsvis algoritmn, præbtinglsn og postbtinglsn, notrr vi ovnstånd som Alg. Dr kan i n algoritm vær mang præ- og postbtinglsr i sving, idt nhvr lill dl af algoritmn (f.ks. n tildling) har sin gn krav og rsultatr. Hvis ikk andt r nævnt, vil vi dog antag, at diss btgnlsr rfrrr til dn kompltt algoritms præbtingls og postbtingls. D simpl tilfæld samt rkursion r bhandlt fint i [1]. Basrt på dtt fokusrr vi blot på whil-løkkr. Problmt md n whil-løkk, dr r omkranst af t sæt præ- og postbtinglsr, r, at dt r t alt for voldsomt dirkt logisk skridt at argumntr for, at postbtinglsn gældr basrt på præbtinglsn, når dr r t a priori ubgrænst antal itrationr gnnm kroppn af n whil-løkk i mllm d to. Af dn grund indførs n ny typ udsagn, kaldt invariantr, hvis opgav dt r at udtrykk sammnhæng mllm d variablr, dr ændrr sig dynamisk i løkkn. Invariantn knyttr sig ligsom præ- og postbtinglsr til n bstmt position i algoritmn; nmlig positionn umiddlbart indn dt boolsk udsagn valurs. For at vi kan brug n invariant til nogt, skal dn naturligvis vær opfyldt (sand), 2
hvr gang vi kommr til dn givn position i algoritmn. Dr ud ovr skal dn vær rlvant (stærk nok) til dt, vi ønskr at brug dn til; nmlig at vis postbtinglsn. Ndnfor ss n lill algoritm (faktisk r dt n dl af t Java-program). // Prcondition: r = 1; q = p; whil /*I*/ (q!= 0) // Invariant: r = r * x; q = q - 1; // Postcondition: Input t til algoritmn r og, og algoritmn skal brgn ; dvs. opløftt i t, hvilkt udtrykks i postbtinglsn. Præbtinglsn r, at r t ikk-ngativt hltal. Invariantn r t udsagn, dr skal gæld hvr gang, vi når til positionn markrt md t I. For nmhds skyld r slv invariantn dog skrvt hlt til højr på samm lini. Indn vi bvisr, at ovnstånd algoritm r partilt korrkt, vil vi s på n gnrl skablon til at bvis dtt for whil-løkkr. Btragt følgnd abstrakt algoritm: // Prcondition: init whil /*I*/ ( ) // Invariant:! body // Postcondition: Hr btgnr init all initialisringrn, dt boolsk udtryk i whil-konstruktionn og body hl whil-løkkns krop. 3
Man kan tablr, at invariantn gældr, vd at vis: 1. 2.!#" init! body! Ovnstånd indfangr formlt kravt om, at invariantn skal vær opfyldt hvr gang, algoritmn kommr til dn pågældnd position. Først krav udtrykkr, at invariantn skal vær opfyldt først gang, og andt krav udtalr sig om rstn: Hvis vi kommr til invariant-positionn, og dt ikk r først gang, må vi hav vært dr før, og på dt tidspunkt må drfor hav vært opfyldt, ligsom! skal hav vært opfyldt. Lad os nu s på, om invariantn for vors ksmpl-algoritm gældr. For at hold styr på værdirn af n algoritm-stumps variablr på forskllig tidspunktr brugr vi umærkd variablnavn til at btgn variablrns værdir før udførlsn af n algoritm-stump og mærkd ftr udførlsn (vi gør dt kun for variablr, dr faktisk ændrr værdi). Først skal vi vis: $$ r = 1; q = p; &%')(* Vd indsættls af værdirn % % og /' 0,, hvilkt r sandt. Drnæst skal vi vis '10 0 ",32 i udtrykkt r = r * x; q = q - 1; % - (. 5%' ( fås Vi antagr som allrd forklart, at først udsagn r sandt og skal så vis dt %6. Nu kan vi vis sidst. Fra algoritmn har vi &%67 8' og,,9 5%':(;=>?'*ACBEDF '10 hvor sidst lighd følgr af antaglsn. Nu kan vi altså vis invariantr, mn hvad r forbindlsn til postbtinglsn, som jo r dt, vi gntligt intrssrr os for? Hl idén r, at invariantn kan brugs til at vis postbtinglsn.
_ W I I Hvis vi kommr til postbtinglsn, så vd vi dls, at dt boolsk udsagn i whilkonstruktionn må vær falsk (llrs var vi jo ikk kommt ud af whil-løkkn), mn vi vd også, at invariantn r sand, fordi vi lig var vd invariant-positionn for at chck. Hvis dt r vist, at invariantn! gældr for n whil-konstruktion, kan partil korrkthd tablrs vd at vis:!#"$gh Lad os på dnn måd vis partil korrkthd af vors ksmpl-algoritm. Vi skal altså vis, at '1 7K "JG,32 LM L Da G,2 r nsbtydnd md, udsagnt 8QR0, hvilkt r nsbtydnd md., får vi vd indsættls i NMOP rminring I dtt afsnit angivs n skablon brgnt på at bvis, at n whil-løkk trminrr. Idén r at find t llr andt, dr blivr mindr ftr hvrt gnnmløb, og som ikk kan bliv vilkårligt lill. Dt vil vi nu udtrykk formlt. Vi ladr S btgn all variablrn i algoritmn og ønskr nu at kunn dfinr n funktion af diss variablr. il dt formål ladr vi S D btgn værdirn af all variablrn i algoritmn først gang invariant-positionn nås. Gnrlt btgnr SU værdirn af all variablrn dn V t gang invariant-positionn nås. En algoritm trminrr, hvis dr finds n trminringsfunktion WYXZS\[], så 1. ^*V`_ 2. ^*V`_ XaW XaW SU Ub SU SUdc D 5
, W _, % _ W % Intuitionn r, at da funktionn har n startværdi af n givn ikk-ngativ størrls (da W S D ), og da funktionn aftagr md mindst én i hvrt gnnmløb af whil-løkkn (andt krav) og ikk kan bliv ngativ (først krav), da må algoritmn trminr. Invariantn, som jo allrd r vist, må naturligvis brugs til diss argumntr, hvis dt r rlvant. For vors ksmpl-algoritm kunn man vælg trminringsfunktionn WYX f Z 5 [ dfinrt vd W g h - H,i,i Vi vrificrr nu kravn. Vi startr md dt andt krav: j h - `,k,k,idc Dml b,kdc D j dc D -dc D Z dc D,kdc D Dt r også klart, at dt først krav r opfyldt, mn vi kan faktisk ikk bvis dt formlt basrt på dn nuværnd invariant. For at vis dt, kunn dt vær rart, hvis invariantn var!nx 10 "o,np Så vill punktt følg dirkt af dludsagnt,np. Mn hvis invariantn ændrs, skal vi naturligvis bvis forfra, at dn gældr. Lad os s på dn ny dl,np. Først gang vi kommr til invariant-positionn følgr dt af, at,, og at dtt udsagn holdr for (præbtinglsn). Vi har drfor (md gnbrug af dt tidligr bvis for dn rstrnd dl af invariantn) Jp r = 1; q = p;?'10 ",qp For d øvrig gang skal vi antag invariantn, og at btinglsn q!= 0 r sand og vis, at når kroppn r udført, r invariantn ign sand. u Mn hvis,rs og,t2, da må,v_. I kroppn udførs q = q - 1, så %6,9. Dt btydr klart, at, og drmd, p. Md gnbrug af dt tidligr bvis for dn rstrnd dl af invariantn har vi 7!#"3,32 hvor! r dn ny invariant angivt ovnfor. 6 r = r * x; q = q - 1;!
Dsign af invariantr Dt sidst, dr manglr for at gør bhandlingn af whil-løkkr fuldstændig, r n rækk rglr for, hvordan invariantr dfinrs. Dsværr kan man ikk opstill rglr, dr md garanti førr frm til t bvis. Ovrrasknd nok kan man faktisk bvis, at sådann rglr ikk kan ksistr! Formlt st r situationn faktisk ndnu værr, idt dr bvisligt finds algoritmr md præ- og postbtinglsr, sådan at postbtinglsn altid r sand, hvis man startr i n situation, hvor præbtinglsn r sand, mn hvor dr simplt hn ikk ksistrr t bvis for at dt r tilfældt! D situationr r dog mgt kstrm, og man kan hldigvis komm mgt langt md nogl tommlfingrrglr og lidt rfaring. Dt bdst råd r at tag udgangspunkt i postbtinglsn, som jo r dn, man virklig ønskr at vis. Normalt skal man forsøg at gnralisr dn, så dn udtalr sig om d variablr, dr ændrr sig i kroppn. Samtidigt kan man hold sig for øj, at når dt boolsk udtryk i whil-løkkn blivr falsk, så skal dt sammn md invariantn kunn brugs til at vis postbtinglsn. Littratur [1] Sara Baas and Alln Van Gldr. Computr Algorithms: Introduction to Dsign & Analysis. Addison-Wsly, 2000. 7