Programmeringsskolan - Lektion # 2
Lektion #2 - Skriva program, nyckelord, funktioner, kommentarer
Ditt första program:
Hittils har ni bara skrivit kommandon i Pythontolken för att få Python att göra något. Nu är det dock dags att bli en riktig Pythontjusare och börja skriva riktiga program!
Pythonprogram kan skrivas i vilket textredigerare som helst, men de flesta föredrar att ha en speciell editor för ändamålet. I IDLE finns en sådan editor inbyggd, som startas genom att välja File -> New Window. Några andra populära editorer är PyScripter och Komodo Edit. IDLE-editorn räcker dock gott och väl för ändamålet och jag rekommenderar er att köra den så länge.
Skapa en ny fil och skriv följande:
print "Spam, spam, spam"
Spara filen som "spam.py". Du kan köra programmet antingen genom att dubbelklicka på den i din filbrowser eller genom att välja Run -> Run Module i IDLE-editorn. Du bör få följande utskrift:
Spam, spam, spam
Det som händer är att Pythontolken går igenom vårt program, rad för rad, och utför instruktionerna vi har skrivit. Strängar - som "Spam, spam, spam" - har vi tagit upp tidigare, men vad är "print" för någonting?
Nyckelord och operatorer:
print är ett av cirka 30 nyckelord som finns i Python. Nyckelord, samt operatorer (som *, =, +, etc. ) är grundstenarna i ett programspråks syntax. Precis som du använder verb, substantiv och adjektiv när du pratar med människor använder du operatorer och nyckelord när du pratar med Python. print är alltså ditt sätt att tala om för Python att du vill skriva ut någonting på skärmen.
Vi testar att göra ett till program bara för att det är så kul:
print "Python, hur många sekunder går det på ett dygn?"
hours = 24
minutes = hours * 60
seconds = minutes * 60
print seconds
Programmet ger utmatningen:
Python, hur många sekunder går det på ett dygn?
86400
Visst, det här funkar, men att bara spotta ur sig en siffra känns nästan lite oförskämt. Vi gör programmet lite artigare:
print "Python, hur många sekunder går det på ett dygn?"
hours = 24
minutes = hours * 60
seconds = minutes * 60
print "Svar: Det går", seconds, "sekunder på ett dygn"
Vilket ger utmatningen:
Python, hur många sekunder går det på ett dygn?
Svar: Det går 86400 sekunder på ett dygn
Som ni ser går det bra att blanda text och variabler i utskriften. Vi kan även spara in några rader genom att skriva hela uträkningen som ett enda uttryck och direkt skriva ut det:
print "Python, hur många sekunder går det på ett dygn?"
print "Svar: Det går", 24 * 60 * 60, "sekunder på ett dygn"
En viktig insikt:
Att vi lika gärna kan skriva en siffra, en variabel eller ett helt uttryck beror inte på någon speciell egenskap hos print. Anledningen är att det fungerar är att de alla går att tolka som värden (i det här fallet av typen heltal) och därför är ekvivalenta. Där Python förväntar sig ett värde går det därför alltid lika bra att skriva ett värde, en variabel, eller ett uttryck.
Funktioner:
Vad är en funktion? En funktion, i programmeringstermer, tar en viss indata (som kallas argument), utför en mängd instruktioner och lämnar ifrån sig ett värde (som kallas funktionens returvärde). En lite enklare liknelse man brukar använda är att funktioner är som verb i grammatiken - man har något som gör någonting med något annat.
Om du inte använde en räknesticka i skolan har du säkert använt din miniräknare för att t.ex. ta fram roten ur ett tal - du har då använt en funktion. Talet du matar in är funktionens argument och resultatet är funktionens returvärde.
print är ganska lik en funktion - den tar ett argument och skriver ut det på skärmen. Vi kan testa att göra en funktion som tar ett tal som argument och ger kvadraten av talet som returvärde:
När man skriver en funktion kallas det att man definierar den. Skapa ett nytt dokument och skriv följande:
def square(x):
_ _ result = x * x
_ _ return result
Vad har vi gjort? Jo, vi har definierat en funktion som heter square och som tar en parameter x. De indenterade raderna är de instruktioner som ska utföras när vi kör - eller anropar, som det heter - vår funktion. Den sista raden börjar med nyckelordet return - return gör att "result" blir vår funktions returvärde, d.v.s. vi säger åt funktionen att mata ut "result".
OBS! return avslutar även funktionen, så du kan inte lägga några instruktioner efter return.
Det här innebär alltså att vi var som helst i programmet kan anropa square(x), förutsatt att vi gör det på en rad som ligger efter definitionen. (Python kan nämligen inte anropa funktioner innan man har definierat dem.)
Istället för att skriva
y = x * x
kan vi nu göra samma sak genom att skriva
y = square(x)
Ändra ditt program så att det ser ut så här:
def square(x):
_ _ result = x * x
_ _ return result
a = 50
print "Kvadraten av", a, "är:", square(a)
Spara programmet som "square.py" och kör.
Mer om funktioner:
En skillnad mellan funktioner i matematiken och funktioner i Python är att Pythonfunktioner kan vara utan argument och returvärden. T.ex. kan vi definiera en funktion på följande sätt:
def dead_parrot_sketch():
_ _ print "This parrot is no more!"
_ _ print "It has ceased to be!"
_ _ print "It has expired and gone to meet its maker!"
och anropa den som så:
dead_parrot_sketch()
vilket ger utmatningen:
This parrot is no more!
It has ceased to be!
It has expired and gone to meet its maker!
Vi har testat att skriva funktioner med ett argument och funktioner utan argument. På samma sätt kan vi definiera funktioner som tar fler än ett argument - den här funktionen räknar ut längden på en rätvinklig triangels hypotenusa genom att ta längden på dess sidor som indata:
def calculate_hypotenuse(a, b):
_ _ length = (a ** 2 + b ** 2) ** 0.5
_ _ return length
(** betyder "upphöjt till" i Python)
Nyttan med funktioner:
Låt oss säga att du ska skriva ett program där du kommer att behöva göra om grader till radianer. Istället för att skriva en hel uträkning varje gång du vill göra konverteringen kan du skriva en funktion som tar ett gradtal som argument och returnerar resultatet i radianer. Vill du sedan ändra på hur konverteringen från grader till radianer går till (man kanske har glömt att hantera fall där gradtalet > 360, t.ex.) så behöver du bara ändra på ett enda ställe i koden.
Funktioner är inte bara praktiska genom att de sparar tid - att på ett bra sätt dela upp de uppgifter ditt program ska utföra i funktioner gör dessutom koden mer lättläslig och strukturerad. Tänk på sakerna ditt program ska göra som en mängd verb - flytta spelaren, uppdatera skärmen, etc. - och dela upp det i funktioner därefter.
Skriv aldrig samma kod två gånger!
Som jag nämnde ovan så är en fördel med funktioner att man slipper skriva samma instruktioner flera gånger, men praxisen att återanvända kod, och att försäkra sig från att behöva skriva om saker, omfattar inte bara funktioner.
Säg att du har gjort ett spel där spelaren börjar med 100 hitpoints, och att spelarens hitpoints sparas i en variabel "hp". Låt oss säga att spelet även har powerups som återställer spelarens hitpoints till 100.
Dock kanske 100 hitpoints är alldeles för lite att börja med, så du ändrar det till 200. Men! Har du kvar definitionen att "hp" sätts till 100 när spelaren plockar upp en powerup får du problem - en spelare med 200 hitpoints som tar powerupen kommer att förlora halva sin livmätare!
Vad sägs om att spara mängden hitpoints spelaren börjar med i en variabel "start_hp"? På så sätt kan vi istället för att sätta "hp" = 100 sätta "hp" = "start_hp". Precis som i fallet med funktionerna så kan vi ändra funktionaliteten på flera ställen i programmet genom att bara ändra på en enda rad.
Att göra lite extra arbete nu för att slippa göra väldigt mycket onödigt arbete senare är en vanlig praxis inom programmering, och något man bör ha i tankarna.
Det passar bra att avsluta med de där visdomsorden, så nu får det räcka - det blev en väldigt lång lektion den här gången! Lämna gärna kommentarer om innehållet - Går det för fort fram? Är något oklart eller blir det för tjatigt?
Om ni har några frågor som gäller programmering, ställ dem i forumtråden!
Övningar tills nästa gång:
* Skriv en funktion "absolute_value(x)" som returnerar absolutvärdet av x.
* Skriv en funktion som räknar om grader till radianer. Använd %-operatorn (modulo) för att ta hand om tal större än eller lika med 360.
* I Python finns en rad inbyggda funktioner. "input()", som vi ska titta mer på nästa gång är en av dem. Ta en tjuvtitt genom att leta efter "input()" i Pythondokumentationen och skriv ett program som använder funktionen.
* Lämna lite feedback om lektionerna, antingen här i bloggen eller i forumtråden! Som sagt, så fort det är något ni tycker är konstigt eller ni undrar över, säg till!
* Fundera över vad för sorts spel ni vill göra som slutprojekt och skriv vad ni tycker, antingen här eller på forumet!
Hmm hur vet man vilken datatyp ens variabel är (om det ens finns i python)?
Vad händer om man har en funktion som:
def square(x):
__ result = x * x
__ return result
och skickar in variablen
my_var1 "spam spam spam"; ?
Mycket bra fråga. Datatyper finns i Python, men man kan säga att de är delvis bortabstraherade - Python använder något som kallas för "duck typing" efter frasen "If it walks like a duck and quacks like a duck, I would call it a duck".
Det här innebär alltså att om typen har de egenskaper som behövs så kör man bara på utan att vidare bry sig om exakt vilken typ det är.
Det som händer när man gör det som du beskrev är att Python i runtime ser om det går att göra multiplikationen, och om det inte går så får du ett runtimefel.
Något som kommer i nästa lektion är metoder för att casta typer - int(x) returnerar t.ex. x, omtolkad till en integer.