Matematik Gymnasieskola Modul: Matematikundervisning med digitala verktyg II Del 4: Programmering i matematik Programmering i matematik Ola Helenius, NCM och Morten Misfeldt, Aalborg universitet Matematik är ett ovanligt ämne eftersom det å ena sidan består av sina objekt, som fem, cirklar, rationella tal, polynom och fyrdimensionella kuber, och å andra är ett utövande. När man i kursplanen har valt att skriva fram förmågor som syftet med matematikundervisningen, så är det ett utslag av att lyfta fram matematiken som en handling, det vill säga det som människor gör när de är matematiska; de löser problem, utvecklar och använder olika matematiska begrepp, representationer och rutiner. Ibland säger man att matematiken är autopoietisk, självgenererande. Det är genom att vara matematisk som man skapar matematik, och man är matematisk när man sysslar med matematiska begrepp. Programmering kan anknytas till båda sidorna av matematiken. Det kan vara en teknik för att hantera matematiska objekt men också i sig fungera som en matematisk teknik. Vi kan ställa flera frågor som är matematiska till sin natur men som också har en didaktisk sida. 1. Vilka matematiska problem kan man lösa med programmering? Vilka är lämpliga att arbeta med ur ett undervisningsperspektiv, och varför? Hur ska det i så fall gå till? 2. Vilka matematiska objekt kan programmeras? Eller mer exakt: vilka matematiska objekt kan representeras med eller via programmering? Vilka är lämpliga att arbeta med ur ett undervisningsperspektiv, och varför? Hur ska det i så fall gå till? 3. Vilka tekniska och matematiska kunskaper och resurser behövs för att arbeta med dessa problem och objekt (punkt 1 och 2)? 4. Vilka egenskaper har programmeringsbaserade lösningar av ett givet problem, i sig själva eller i jämförelse med lösningar baserade på andra tekniker? Även om det inte finns några generella svar på frågorna ovan, så är det just sådana frågor som hjälper oss att förstå de didaktiska dilemman som uppkommer när man arbetar med programmering i matematiken. Ett dilemma som uppkommer i skolmatematiken är att alla problem som vi är vana att behandla är utvalda för att kunna lösas med sådana metoder och tekniker som man undervisar om. Med programmering får vi tillgång till helt andra tekniker och kan också lösa andra problem. I vissa fall kan programmering erbjuda intressanta alternativa möjligheter att behandla problem som redan är bekanta från skolmatematiken. Men om man inte också börjar att använda sig av problem som normalt inte behandlas i https://larportalen.skolverket.se 1 (8)
skolmatematiken, så kommer man inte att på allvar kunna illustrera programmeringens förtjänster som matematisk problemlösningsverktyg. De flesta programmeringsuppgifter så här långt i modulen har handlat om att programmera något som i sig inte är ett matematisk problem, men där matematik på olika sätt används i arbetet eller för att representera till exempel en rörelseriktning, position eller slumpfenomen. I del tre modellerade vi exempelvis ett praktiskt tärningsproblem genom att göra en simulering. Skulle vi lösa samma problem analytiskt så skulle vi behöva tillämpa ganska avancerad kunskap från sannolikhetsläran. Men när vi kodade simuleringen, så behövdes inte mycket annan matematik än addition med 1 och jämförelser av tal i området 1-6. Resten av koden handlade om rent programmeringsmässiga detaljer. I denna sista del i modulen ska vi fokusera på att programmera i matematiken, det vill säga när problemet som vi hanterar redan är formulerat i matematiska termer. Tre exempel För att kunna föra en mer generell diskussion om olika användningsområden för programmering i matematiken inleder vi med tre exempel. Exempel 1. Euklides algoritm Euklides algoritm är ett smart men elementärt sätt att hitta den största gemensamma delaren till två tal. I sin mest basala form utnyttjar den bara ett antal subtraktioner. Största gemensamma delaren av 40 och 15 kan finnas genom att först subtrahera 15 så många gånger det går (innan resultatet blir negativt). 40-15=25 25-15=10 Man tar sedan det senaste subtraherade talet och från detta subtraherar man det senaste svaret och repeterar så många gånger det går. 15-10=5 I detta fall bara en gång. Sedan repeterar man processen. 10-5=5 5-5=0 Den sista icke-försvinnande resten, 5 i vårt fall, är den största gemensamma delaren. Ett bevis för att algoritmen fungerar finns på Wikipedia, sök på Euclid s algorithm. Euklides algoritm är mycket användbar, till exempel när man arbetar med bråk och ofta just vill hitta den största gemensamma delaren, men även när man till exempel löser diofantiska ekvationer. Eftersom vi redan ovan har beskrivit det hela som en algoritm, är det inte så svårt att tänka sig att det hela kan implementeras som kod. Redan den variant som skissas ovan går att koda, men det finns också varianter som kan göras extremt kompakta, på två rader faktiskt, genom att utnyttja restklassaritmetik (moduloräkning), vissa logiska https://larportalen.skolverket.se 2 (8)
funktioner och rekursion. I Python är en extremt kompakt implementering av Euklides algoritm följande: def euklides(a, b): return b and euklides(b, a%b) or a Kör man sedan euklides(4294967297,4487) får man närmast omedelbart svaret 641. Här utnyttjas både ändamålsenlig matematik, speciella egenskaper hos de logiska funktionerna and och or i Python samt en smart rekursion, dvs att programmet anropar sig själv. Men mellan denna variant och den helt elementära finns många mellanting. En lektion om programmering av Euklides algoritm kan läggas upp på olika sätt beroende på elevernas tidigare erfarenheter. Det kan röra sig både av begreppet största gemensamma delare, Euklides algoritm i sig och av programmering. Just eftersom det finns så många olika sätt att implementera algoritmen, från en mycket elementär till en mycket kompakt, så finns det potential att variera och utveckla en lektion på detta tema. Exempel 2. Geometri som rörelse Betrakta geometriproblemer i figur 3. Hur lång är kvadratens sida? Figur 1. Detta problem går att lösa med flera olika klassiska geometriska tekniker som går ut på att dra vissa hjälplinjer och sedan till exempel utnyttja kongruens mellan vissa trianglar. Men vi ska studera en lösning av ett annat slag, som går att implementera även i en visuell programmeringsmiljö som Scratch eller turtle graphics i Python. Vi tänker oss att origo är i nedre vänstra hörnet (kalla punkten A) och sträckan 14 är i x-led. Vi kör 14 cm framåt, svänger 90 grader vänster, kör 7 cm, svänger 90 grader höger och kör 9 cm. Då är vi i motsatt hörn (C). Sedan mäter vi, eller använder Pythagoras sats, för att räkna ut avståndet till utgångspunkten vilket är kvadratens diagonal, d. Vet man att sidan är 1/ 2 gånger diagonalen kan man räkna ut svaret på frågan direkt. Men man kan också fortsätta att använda samma teknik för att rita ut kvadratens andra hörn och, om man vill, hela kvadraten. Man kan gå från C mot A halva diagonalens längd, d/2, och då vara i kvadratens centrum. Man kan svänga 90 grader och gå d/2 och vara i ett nytt hörn (B) sedan svänga https://larportalen.skolverket.se 3 (8)
180 grader och gå då i den riktningen och då få det sista hörnet (D). Sedan kan man mäta en sida. Den ritade kvadraten har en annan orientering än den på bilden, men sidan är ju densamma. Se figur 4. B C A Figur 2. D I en programmiljö som Scratch är detta relativt enkelt att implementera eftersom miljön är byggd bland annat för att kunna styra figurer på skärmen. I Python är det mer komplext, men med hjälp av t ex Turtle Graphics för Python kan man utföra instruktionerna och rita resultatet som skissas ovan med några få enkla kommandon, ungefär som i Scratch. Exempel 3. Kurvlängder Vårt tredje exempel på programmering som matematisk teknik handlar om kurvlängder. I gymnaseiets kurser ingår normalt inte att beräkna längden av kurvor. Omkretsen av en cirkel kan ses som en kurvlängd, men där används ju en specifik formel, inte någon generell metod. Analytiskt kan man beräkna funktionskurvors längder med hjälp av integraler. Ofta blir integralerna dock svåra att beräkna med de metoder som finns tillgängliga i gymnasieskolan. Men med programmering kan man göra andra sätt och approximativt beräkna längden av nästan vilken funktionskurva som helst. Om vi ska beräkna längden av f(x) mellan punkterna a och b, så kan vi helt enkelt dela in intervallet [a,b] i ett antal delar. Vi får en serie x-värden x 0 =a, x 2, x 3,, x n =b. För varje intervall som bildas kan vi med avståndsformeln räkna ut längden på den räta linjen mellan punkterna (x i,f(x i)) och (x i+1,f(x i+1 )). Sedan summerar man längderna och får en appoximation av hela kurvans längd. Nedan har vi till exempel ritat ut kurvan f(x)=x 2 sin(4x), delat sträckan från 1 till 3 i åtta delar och ritat ut den sekvens av linjestycken som approximerar kurvan och som vi alltså kan använda för att approximera längden. Men kan ana att om vi istället skulle dela sträckan i 100 delar så skulle approximationen bli rätt bra. https://larportalen.skolverket.se 4 (8)
Figur 3. En lektion baserad på approximation av kurvlängder kan dels innehålla moment där man med mer eller mindre stöd konstruerar själva programmet. Kanske är det bra att även rita ut funktionskurvan och approximationen för att få en visuell indikation på hur bra approximationen matchar. Man kan även diskutera tekniken att testa allt finare indelningar (10 delar, 100 delar, 1000 delar etc) och få en indikation på noggrannheten genom att se hur den beräknade längden konvergerar. Andra övningar kan vara att beräkna längden på en halvcirkel, där man ju med den vanliga formeln för cirkels omkrets har ett facit att jämföra med. En ytterligare undersökning kan vara att fråga sig om det finns kurvor där den här tekniken funkar dåligt (tänk till exempel på sin(1/x) nära 0). Karakterisering av de tre exemplen De tre exemplen ovan är av olika karaktär. I Euklides-exemplet skapas ett matematiskt verktyg. Om man har en viss klass av problem som man kan skapa en algoritm för att lösa, så kan man också omvandla algoritmen till kod och därigenom skapa ett matematisk verktyg. Oftast är det svårare att skapa koden än att lösa ett problem, men fördelen med koden är att när programmet väl är klart snabbt kan lösa alla problem i den givna klassen. I fallet med Euklidesprogrammet används dessutom datorns egenskap att mycket snabbt kunna genomföra många beräkningar. Att hitta den största gemensamma delaren till 40 och https://larportalen.skolverket.se 5 (8)
15 går är ju enklare att göra för hand än genom att skapa ett programbaserat verktyg för saken. Men om vi vill ta reda på den största gemensamma delaren till 4294967297 och 4487 så kommer man att få arbeta en bra stund mede den manuella metoden, medan att program levererar svaret på ett ögonblick. Euklides algoritm är relativt enkelt att förstå konceptuellt, men arbetssamt att hantera med papper och penna så snart talen blir någorlunda stora. Det är just därför det är lämpligt att programmera så att en dator får sköta beräkningarna. Sådana här fall, eller fall där man vill göra ett stort antal likartade beräkningar, är typiska kandidater för när det är lämpligt att programmera ett matematiskt verktyg. Geometriexemplet är, till skillnad från frågan om största gemensamma delare, inte så intressant annat än som en uppgift att lösa. I just det här fallet var det inte datorns beräkningskraft som vi var ute efter. Istället visade det sig att specifika möjligheter i en viss programmeringsmiljö skapade alternativa sätt att tänka på problemet. När man väl har löst uppgiften med hjälp av ett program så inser man kanske att samma tankesätt (pythagoras sats) går att använda även med papper och penna. Den som inser det har kanske för alltid fått ett utvidgat sätt att se på geometri. Värdet här var alltså inte programmet i sig, utan de matematiska resonemang som blev en följd av att angripa problemet med programmering. Det är svårt att veta på förhand om ett visst problem är intressant att angripa med programmering, det vill säga om det kommer att ge några speciella matematiska insikter att göra så. Exemplet med kurvlängder liknar till viss del exemplet om Euklides algoritm. Vi kan slå in nästan vilken funktion som helst och med tillräckligt fin indelning av intervallet så kan vi får en bra approximation av funktionskurvans längd. Så, på sätt och vis, även här har vi skapat ett verktyg. Men det finns också en viktig skillnad. I Euklidesexemplet så var det samma algoritm som man också använder när man hanterar problemet analytiskt som var utgångspunkten för programmet. Men i kurvlängsexemplet så utgår vi från en helt annan teknik och eftersom den analytiska tekniken i praktiken är för svår för gymnasiets kurser, så har vi med hjälp av programmeringen fått en helt ny klass av geometriska objekt som vi kan hantera, nämligen längder av funktionskurvor. Ett sätt att tänka om orkestrering av lektioner Som vi ser ställer undervisning om och med programmering i matematikundervisningen speciella krav. Det kan vara att få möjlighet att bekanta sig med och lära sig programmeringsmiljön och att få möjlighet att experimentera, genom tinkering eller modifikation av kod som andra har gjort. När programmering ska användas i matematiken är det rimligt att det är än större fokus på det matematiska innehållet. De tre exempel som vi har givit ovan är lämpliga för olika gymnasiekurser och matematiken i dem är utmanande i olika grad. I modulens tidigare delar har lärarledda diskussioner av det matematiska innehållet med fördel kunnat placeras i slutet av lektionen. Eleverna kan ju mycket väl ha använt olika matematiska idéer eller principer för att med programmering lösa samma uppgift, eller så har de arbetat med olika uppgifter. Läraren kan då lyfta det matematiska i https://larportalen.skolverket.se 6 (8)
efterhand. Men när programmering ska användas för matematiska syften, är det rimligt att anta att det matematiska innehåll som eleverna ska möta kräver en introduktion av läraren. Kanske behöver även relevanta programmeringstekniker eller nya kommandon introduceras. Det kan också vara lämpligt att hålla klassen mer samlad runt ett gemensamt matematiskt innehåll eller ett gemensamt problem. De lektionsförslag som finns i den här delen baseras alla på sådana orkestreringsmönster. Nästa avsnitt beskriver ett möjligt upplägg. Lektionsplanering Det är bra att före lektionen tänka igenom vilka matematiska begrepp och procedurer som aktiviteten kommer att innehålla och att fundera igenom vilka av dessa som betraktas som förkunskaper och vilka som du vill att eleverna ska utforska eller öva på. Om du repeterar eller lämnar ut formelblad eller liknande för det som du ser som förkunskaper kan dessa begrepp och procedurer användas på ett instrumentellt sätt av eleverna och inte i onödan stoppa dem i arbete med de begrepp och procedurer som ska utforskas. Fundera före lektionen också igenom vilka programmeringsrelaterade tekniker eller metoder som kommer att behövas och vilka av dessa du betraktar som förkunskaper och vilka som du snarare vill att eleverna ska utforska eller öva på. Lämna också inom detta område ut instruktioner för det som du anser är förkunskaper, så att delar av koden kan användas på ett instrumentellt sätt av eleverna och inte i onödan stoppar dem i arbetet med att utforska relationerna mellan matematiska representationer och kodrepresentationer. Planera hur du ska summera lektionen eller lektionsserien. Lyft denna avslutning till att inte handla om svaren på konketa uppgifter utan om a: vilka matematiska begrepp och prodecurer vi har utnyttjat, och b: vilka programmeringstekniker vi har utnyttjat. Var här extra noga med terminologi och precision, inte genom att rätta eleverna utan genom att själv omformulera elevernas kommunikation i exakt form. Sammanfattning av modulen Den här modulen har handlat om programmering i matematikundervisningen. Ämnesplanernas skrivningar innebär att programmering ska användas till att lösa matematiska problem, inte utbilda eleverna i programmering. Detta har påverkat modulens innehåll. Men med ledning från forskningen om tekniska hjälpmedel från bland annat Trouche så har vi påpekat att även om målet är matematik, så är det viktigt att också ge tillräcklig uppmärksamhet på att lära sig verktyget, programspråket och programmeringsmiljön i det här fallet. Även när det långsiktiga målet är att lösa matematiska problem, så är det ibland en bra idé att starta med att programmera sådant där den direkta uppgiften handlar om att modellera, styra eller på annat sätt hantera något som inte är matematiskt i sig. Av samma skäl är det ibland lämpligt att börja med matematiska problem som är reletivt enkla, och egentligen kan hanteras lika bra utan programmering. https://larportalen.skolverket.se 7 (8)
Precis som man ofta refererar till vardagliga företeelser när man förklarar matematiska begrepp, så kan arbete med ickematematiska företeelser var en snabbare väg fram till att kunna förstå programmeringens användbarhet i matematiken. Vi har också i högre grad fokuserat på att undersöka och modifiera existerande program än att skapa egna från början. På så sätt kan man snabbare komma till en nivå där programmering går att använda i matematiken. Vi har också i högre grad fokuserat på vilken matematik eller vilka matematiska förmågor som relaterar till programmering än på olika programmeringstekniska begrepp. På det didaktiska planet har vi utgått från att få lärare själva är kompetenta programmerare. Programmeringskomponenterna i lektionerna har därför oftast varit av utforskande karaktär, där läraren inte alltid förväntas ha alla svar färdiga. Men även en sådan här undervisning måste vara välplanerad. Faktiskt mer välplanerad än undervisning som bygger på att läraren ger eleverna explicita instruktioner och förklaringar. Därför har vi också fokuserat på vikten av att tänka igenom hur lektionen orkesteraras och beskrivit olika möjligheter att orkestera lektioner som kan passa i olika sammanhang. En lektion som innehåller programmering är ofta mer komplicerad än andra lektioner eftersom själva tekniken också måste beredas lämplig plats, men också kontrolleras så att den inte tar över. Detta är en del av orkestreringen. Vi tror att eftersom programmering är nytt för många lärare, så är det bättre att tänka sig att det nya momentet byggs in i en existerande matematikundervisning, där läraren har en upparbetad trygghet. Det är av det skälet som modulen har varit upplagd så att den startade med ett större fokus på programmeringstekniska detaljer för att nu i slutet handla om programmeringens roll i själva matematiken. https://larportalen.skolverket.se 8 (8)