Algoritmisk tenkning i problemløsing

Tre krav skiller en algoritme fra en løs beskrivelse: hvert steg må være ENTYDIG (ingen tolkning), rekkefølgen må være bestemt, og den må STOPPE etter endelig mange steg. «Kok opp vann» duger som oppskrift til middag, men ikke som algoritme: «varm vannet til det koker, maks 1010 minutter» gjør det. Framgangsmåten når du skal lage en: løs problemet én gang for hånd, skriv ned nøyaktig hva du gjorde, og bytt så de konkrete tallene med variabler.

abc-formelen

x=−b±b2−4ac2ax = \frac{-b \pm \sqrt{b^2 - 4ac}}{2a}

Diskriminanten

D=b2−4acD = b^2 - 4ac

abc-formelen som algoritme
StegHandling
1Les av a, b og c
2Regn ut b² - 4ac
3Er den negativ: stopp, ingen løsning
4Regn ut de to x-verdiene
5Skriv ut svaret

Tips

  • Test algoritmen på et tilfelle du kan svaret på FØR du bruker den på noe nytt. Finner du feilen der, sparer du deg for å mistolke et ukjent svar.
  • Skriv stegene i punktliste før du skriver kode. Nesten alle programmeringsfeil i 1T er egentlig tenkefeil som ble synlige først i koden.
  • Løs én bit om gangen. Står du fast på et sammensatt problem, del det i mindre biter som hver kan løses for seg: «les inn tallene», «regn ut diskriminanten», «avgjør antall løsninger», «skriv ut svaret». Hver bit blir kort nok til å teste alene, og du finner feil i den ene biten uten å lete gjennom hele algoritmen. Det er nøyaktig samme idé som å regne en lang oppgave i delsvar i stedet for i ett jafs.

Eksempel: Fra hånd-regning til algoritme

Beskriv en algoritme som avgjør om et helt tall nn er et primtall, og bruk den på n=91n = 91.

Løsning:
  1. Vi skal avgjøre om n=91n = 91 er et primtall, og løser først for hånd: et primtall er kun delelig med 11 og seg selv, så vi må teste divisorer
  2. det holder å teste opp til n\sqrt{n}, for en større divisor må ha en mindre partner
  3. for n=91n = 91 er 91≈9,5\sqrt{91} \approx 9{,}5, så vi tester 2,3,5,72, 3, 5, 7
  4. 9191 er ikke delelig med 2,32, 3 eller 55, men 91=7⋅1391 = 7 \cdot 13
  5. algoritmen stopper med én gang den finner en divisor. Tallet 9191 er ikke et primtall.
Algoritmen kjørt på n = 91
DivisorGår opp?Handling
2neifortsett
3neifortsett
5neifortsett
7jastopp: ikke primtall
Alternativ forklaring/metode: Simuler endring steg for steg

Alternativ metode – innenfor pensum, men ikke hovedmetoden her

Euler-steg for modellering

Skal du modellere noe som endrer seg over tid, en bestand, en temperatur, en saldo: kan du dele opp problemet i identiske, gjentatte steg: finn endringen akkurat NÅ, legg den til, og gjenta. Regelen er yny=ygammel+y′⋅Δty_{ny} = y_{gammel} + y' \cdot \Delta t. En bestand på 100100 dyr vokser med 10 %10\ \% av bestanden per tidssteg (y′=0,1yy' = 0{,}1y), med Δt=1\Delta t = 1: steg 1 gir y′=0,1⋅100=10y' = 0{,}1 \cdot 100 = 10, så yny=100+10=110y_{ny} = 100 + 10 = 110 → steg 2 gir y′=0,1⋅110=11y' = 0{,}1 \cdot 110 = 11, så yny=121y_{ny} = 121 → steg 3 gir y′=0,1⋅121=12,1y' = 0{,}1 \cdot 121 = 12{,}1, så yny=133,1y_{ny} = 133{,}1. Samme dekomponerings-idé som abc-formelen delt i biter, bare at «biten» her gjentas mange ganger i en løkke.

Euler-steg: bestand på 100, vekst 10 % per steg
Stegy' = 0,1 · yy_ny = y + y'
0100
110110
211121
312,1133,1
Alternativ forklaring/metode: Finn største felles faktor med Euklids algoritme

Tilleggsinformasjon – ikke pensum på dette nivået

Euklids algoritme (historisk eksempel)

Forutsetninger:

  • Ikke pensum i seg selv (KM403 nevner ingen navngitte klassiske algoritmer), tatt med som et konkret, historisk eksempel på at «entydig, bestemt rekkefølge, stopper» (kriteriene i forklaringen over) er nøyaktig hva som gjør en 2300 år gammel oppskrift til en algoritme like mye som en moderne én.

Den eldste kjente algoritmen som fortsatt brukes i dag: for å finne største felles faktor (SFF) til to tall, del det største tallet på det minste og se på RESTEN. Bytt så ut det største tallet med det minste, og det minste med resten. Gjenta til resten blir 00. Da er det forrige tallet SFF-en. Den STOPPER garantert, fordi resten blir mindre for hver runde, og en synkende følge av hele tall (større enn eller lik 00) må til slutt nå 00.

SFF(84, 36) med Euklids algoritme
Stort tallLite tallRest ved divisjon
843684 = 2 · 36 + 12
361236 = 3 · 12 + 0
Rest 0 → SFF = 12
Alternativ forklaring/metode: Tilnærme en kvadratrot med Herons metode

Tilleggsinformasjon – ikke pensum på dette nivået

Herons metode (historisk eksempel)

Forutsetninger:

  • Ikke pensum i seg selv, av samme grunn som Euklids algoritme over, et historisk eksempel på samme gjenta-til-svaret-stabiliserer-seg-idé som Euler-steget over og Newtons metode i neste undertema, bare nesten 2000 år eldre.

Brukt til å regne ut kvadratrøtter for hånd lenge før kalkulatorer fantes: gjett en startverdi xx for a\sqrt{a}, regn ut et bedre gjett med xny=12(x+ax)x_{ny} = \frac{1}{2}\left(x + \frac{a}{x}\right), og gjenta til svaret slutter å endre seg. Hvert gjett blir automatisk nærmere den sanne kvadratroten, en algoritme kan altså gi et STADIG BEDRE svar i stedet for det eksakte svaret med én gang.

Tilnærme kvadratroten av 10, start x = 3
Stegxx_ny = 0,5(x + 10/x)
033,1667
13,16673,1623
23,16233,1623

Oppgaver

Prøv minst én oppgave på hvert nivå.

Lett(3)

L-21Må en algoritme stoppe etter endelig mange steg?

Vis fasit
  1. En algoritme må terminere
  2. ja, den må stoppe

L-22Er «regn litt til det ser riktig ut» en algoritme?

Vis fasit
  1. «ser riktig ut» kan tolkes ulikt
  2. nei, steget er ikke entydig

L-23Hvor mange divisorer må du teste for å avgjøre om 4949 er primtall?

Vis fasit
  1. For 49 er kvadratroten 7
  2. test til og med 7
Middels(3)

M-21Er 9191 et primtall?

Vis fasit
  1. 91:7=1391 : 7 = 13
  2. nei, 9191 er ikke et primtall

M-22Hvorfor holder det å teste divisorer opp til n\sqrt{n}?

Vis fasit
  1. Kvadratroten av n er grensen
  2. en divisor over den har en partner under
  3. det holder å teste opp til roten

M-23Hva er diskriminanten til x2+2x−3=0x^2 + 2x - 3 = 0?

Vis fasit
  1. a=1a = 1, b=2b = 2, c=−3c = -3
  2. D=4−4⋅1⋅(−3)=4+12=D = 4 - 4 \cdot 1 \cdot (-3) = 4 + 12 = 1616
Vanskelig(3)

V-21Hva bør algoritmen gjøre hvis diskriminanten er negativ?

Vis fasit
  1. En negativ diskriminant gir ingen reell rot
  2. stopp og meld ingen løsning

V-22Hva kalles det å dele et problem i mindre biter?

Vis fasit
  1. Å dele 1 problem i flere små deler
  2. hver del løses for seg
  3. dekomponering

V-23En algoritme tester ALLE tall opp til nn for å sjekke primtall. Er den riktig, og er den god?

Vis fasit
  1. Alle tall opp til n gir riktig svar, men testing til roten holder
  2. riktig, men treg