Övning 6. Ali Tofigh 24 Oktober, 2006

Relevanta dokument
Klasser och objekt, referenser Grundkurs i programmering med Python

729G04 Programmering och diskret matematik. Föreläsning 7

Kodexempel från Programmering 2 Tobias Wrigstad, Ph.D.

Grundläggande datalogi - Övning 1

Föreläsning 8 Programmeringsteknik och Matlab DD1312. Klassmetod. Egen modul

Sätt att skriva ut binärträd

Uppgifter teknik HT17 (uppdaterad v. 40)

Läsöversikt. Föreläsningar 2-6. Genomförande av laborationer

Användarhandledning Version 1.2

Språket Python - Del 2 Grundkurs i programmering med Python

Tentamen i Introduktion till programmering

Föreläsning 13 och 14: Binära träd

Uppgifter till tenta i 729G04 Programmering och diskret matematik. 7 augusti 2015, kl 08:00-12:00

Föreläsningsanteckningar, Introduktion till datavetenskap HT S4 Datastrukturer. Tobias Wrigstad

Introduktion till objektorientering. Vad är objektorientering egentligen? Hur relaterar det till datatyper? Hur relaterar det till verkligheten?

Python. Python är, som Scheme, ett interpreterat språk men det finns kompilatorer för Python.

Python. Python är, som Scheme, ett interpreterat språk men det finns kompilatorer för Python.

Ordlistor, filhantering och ut på webben. Linda Mannila

Python. Datatyper. Mer om datatyper. Heltal - 3 Flyttal - 2,456 Listor - [1,2,3,4] Strängar - spam!

729G04 Programmering och diskret matematik. Python 3: Loopar

Föreläsning 2 Programmeringsteknik och C DD1316. Mikael Djurfeldt

Python. Vi har ofta behov av att behandla datastrukturer på ett enhetligt sätt så att vi kan göra samma sak i flera olika program.

Övning 1 - Abstrakta datatyper

Erfarenheter från labben

Introduktion till programmering SMD180. Föreläsning 12: Klasser och objekt

Mer grafik. Jan Erik Moström

Tenta (TEN3) i kursen 729G04 Programmering och diskret matematik 5 feb 2016, kl 14:00-18:00

Att prova på en enkel Applet och att lära sig olika sätt att hämta data från tangentbordet. Du får även prova på att skapa din första riktiga klass.

Objektorienterad programmering D2

Inom datalogin brukar man använda träd för att beskriva vissa typer av problem. Om man begränsar sig till träd där varje nod förgrenar sig högst två

Programmering och algoritmiskt tänkande. Tema 3, föreläsning 1 Jody Foo

729G04 Programmering och diskret matematik

TDDE44 Programmering, grundkurs

EnKlass. Instans 3 av EnKlass. Instans 2 av EnKlass

Datalogi, grundkurs 1

Grundläggande datalogi - Övning 2

Laboration A Objektsamlingar

Kurslitteraturen. C-nivå Villkorssatser [kap 8] if & elif & else and & or Loopar [kap 9] for

Problemlösning och funktioner Grundkurs i programmering med Python

TUTORIAL: KLASSER & OBJEKT

Programmering I Tobias Wrigstad fredag, 2009 augusti 28

Föreläsning 2 Objektorienterad programmering DD1332. Typomvandling

TENTAMEN OOP

Objektorienterad programmering i Java I

Idag: Centrerad utskrift. Granskning. DD1311 Programmeringsteknik med PBL. Granskning Felhantering GUI. Föreläsning 15.

TDP002 - Imperativ programmering

Laboration: Whitebox- och blackboxtesting

Övningsuppgifter kapitel 8

729G74 IT och programmering, grundkurs. Tema 3. Föreläsning 2 Jody Foo,

Föreläsning 5-6 Innehåll. Exempel på program med objekt. Exempel: kvadratobjekt. Objekt. Skapa och använda objekt Skriva egna klasser

Föreläsning 2 Programmeringsteknik och Matlab DD1312. Programspråk. Utskrift på skärmen

Föreläsning 5-6 Innehåll

Exempel: Exempel: Exempel: Exempel: $djur=array("ko","katt","älg"); foreach ($djur as $d) { echo $d. " "; } Resultat. ko katt älg

Föreläsning 13 Testning och strängar

Föreläsning 2 Programmeringsteknik och Matlab DD1312. Programspråk. Utskrift på skärmen

Föreläsning 18 Filer och avbildningar

Det är principer och idéer som är viktiga. Skriv så att du övertygar rättaren om att du har förstått dessa även om detaljer kan vara felaktiga.

729G04 Programmering och diskret matematik

729G04 Programmering och diskret matematik. Python 2: Villkorssatser, sanningsvärden och logiska operatorer

Föreläsning 10 Datalogi 1 DA2001. Utskrift på skärmen. Syntax. print( Hej ) Hur är det? Hej. print( Hej,end= ) print( Hur är det? ) HejHur är det?

Hur man programmerar. TDDC66 Datorsystem och programmering Föreläsning 3. Peter Dalenius Institutionen för datavetenskap

Föreläsning 2 Programmeringsteknik DD1310. Programmering. Programspråk

Den klassiska programmodellen. Introduktion till programmering D0009E. Föreläsning 11: Filer och undantag. Filsystem. Interaktiva program.

Introduktion till Datalogi DD1339. Föreläsning 3 29 sept 2014

Bankkonto - övning. Övning 2 Skriv en metod, geträntan, som returnerar räntan.

Föreläsning 2 Programmeringsteknik och C DD1316

DD1320 Tillämpad datalogi. Lösning (skiss) till tenta 20 okt 2011

public class BoundedCounter {

Exempel på användning av arv: Geometriska figurer

Funktioner. Linda Mannila

Imperativ programmering. Imperativ programmering konstruktioner i Lisp. Datastrukturer (kap ) arraystruktur poststruktur

Föreläsning 2 Programmeringsteknik och C DD1316. Programmering. Programspråk

Alla datorprogram har en sak gemensam; alla processerar indata för att producera något slags resultat, utdata.

Övningar Dag 2 En första klass

Text och strängindexerade fält Grundkurs i programmering med Python

729G74 - IT och programmering, grundkurs. Dugga.

F9 - Polymorfism. ID1004 Objektorienterad programmering Fredrik Kilander

Föreläsning 2 Programmeringsteknik DD1310. Programmering. Programspråk

Hur man programmerar. Exempel på problemlösning i Python

Övning. Introduktion och förberedelser

732G Linköpings universitet 732G11. Johan Jernlås. Översikt. Repetition. Muddy. Funktioner / metoder. Punktnotation. Evalueringsordning

Använda Python Laboration 1 GruDat, DD1344

Tentamen ID1004 Objektorienterad programmering October 29, 2013

Objektorienterad Programmering (OOP) Murach s: kap 12-16

MATLAB. Python. Det finns flera andra program som liknar MATLAB. Sage, Octave, Maple och...

Tentamen DE12, IMIT12, SYST12, ITEK11 (även öppen för övriga)

LÖSNINGSFÖRSLAG Programmeringsteknik För Ing. - Java, 5p

Introduktion till programmering SMD180. Föreläsning 8: Listor

Abstrakta datatyper Laboration 2 GruDat, DD1344

Skolan för Datavetenskap och kommunikation PROGRAMMERINGSTEKNIK FÖRELÄSNING 15

Länkade listor, stackar och köer

ITK:P1 Föreläsning 1. Programmering. Programmeringsspråket Java. Stark typning Explicit typning Strukturerat Hög säkerhet

Besiktningsprotokollet

TENTAMEN OOP

Introduktion till programmering D0009E. Föreläsning 9: Tupler och dictionaries

Strängar. TDDD64 Programmering i Python Föreläsning 4. Peter Dalenius Institutionen för datavetenskap

Tentamen i Grundläggande programmering STS, åk 1 lördag

Laboration 3 HI1024, Programmering, grundkurs, 8.0 hp

Sökning i ordnad lista. Sökning och sortering. Sökning med vaktpost i oordnad lista

Datalogi för E Övning 3

Transkript:

Övning 6 Ali Tofigh 24 Oktober, 2006 1 Sortering Att sortera behöver man göra väldigt ofta i programmering. Python tillhandahåller bland annat en metod i listor för detta ändamål. Det enda metoden behöver veta för att kunna sortera elementen är hur par av element jämförs med varandra. Vi ska se tre olika sätt att åstadkomma detta. Vi börjar med en enkel klass, Rectangle, vars instanser har två attribut; width och height. Vi skriver även en metod area som beräknar arean, och två metoder som bör kännas som standard vid det här laget, nämligen metoderna init och str. Dessutom lägger vi till en speciell metod som heter cmp. Denna används av Pythons sort-metod för att sortera listan. Mer om den längre ner. class Rectangle(object): def init (self, width, height): self.width = width self.height = height def str (self): return "w:" + str(self.width) + "\th:" + str(self.height) def area(self): return self.width * self.height def cmp (self, other): if self.height < other.height: return -1 elif self.height > other.height: return 1 else: return 0 Om vi nu har en lista av rektanglar och anropar metoden sort kommer rektanglarna i listan att sorteras i stigande höjd, dvs rektangeln med minst höjd kommer att vara först i listan. Detta beror på att sort letar efter den 1

speciella metoden cmp i de objekt som finns i listan och använder den för att jämföra objekten med varandra. Det som skickas tillbaka från cmp förväntas vara ett tal som är mindre än noll om parametern self ska vara före other i den sorterade listan, större än noll om self ska vara efter other i den sorterade listan, och noll om båda parametrarna är likvärdiga och deras ordning inte har någon betydelse. Titta nu igenom koden för cmp ovan och försäkra dig om att du förstår nedanstående kod: l = [Rectangle(1,7), Rectangle(3, 4), Rectangle(5,2), Rectangle(2,6)] for r in l: print r l.sort() for r in l: print r Hade vi inte skrivit metoden cmp hade rektanglarna sorterats efter deras minnesadress vilket vi inte har någon kontroll över. Observera att man ska skriva metoden cmp i de klasser där instanserna har en naturlig ordning. Vårt exempel med rektanglar är bara till för att illustrera den tekniska biten. Det hade till exempel varit mer naturligt att skriva en cmp -metod för en klass Rational som hanterar rationella tal. Ett annat sätt att sortera är att skriva en funktion och skicka denna till sort. Detta är användbart om man vill kunna sortera på olika sätt i samma program, eller om klassen man använder sig av inte har en lämpligt cmp -metod. Anta t ex att vi vill sortera våra rektanglar efter bredd istället för höjd. Vi kan då skriva en funktion som vi skickar till sort och därmed kommer sort att använda denna för att jämföra objekten i listan istället för cmp -metoden. def cmp_width(r1, r2): if r1.width < r2.width: return -1 elif r1.width > r2.width: return 1 else: return 0 Nu kan vi skriva: 2

l = [Rectangle(1,7), Rectangle(3, 4), Rectangle(5,2), Rectangle(2,6)] for r in l: print r l.sort(cmp = cmp_width) for r in l: print r Ett tredje sätt att få sort att jämföra objekt på det sätt vi vill, är att skicka med en metod. Objekten kommer då att sorteras efter det värde som metoden skickar tillbaka. Om vi till exempel vill sortera på rektanglarnas areor kan vi göra följande: l = [Rectangle(1,7), Rectangle(3, 4), Rectangle(5,2), Rectangle(2,6)] l.sort(key = Rectangle.area) for r in l: print r Observera att det är lite skillnad mellan att sätta sorts cmp-parameter till en funktion och att sätta dess key-parameter till en metod. I det senare fallet kommer metoden att anropas för objekten och metodens returvärde kommer att jämföras för att bestämma objektens ordning! Metoden sort tar tre parametrar, varav två är de som vi redan sett, nämligen cmp och key. Det tredje heter reverse och är satt till False som default. Om man sätter reverse till True kommer listan att sorteras baklänges. Vill vi till exempel sortera rektanglar efter bredd med störst bredd först kan vi återanvända vår funktion cmp_width och sätta reverse till True: l = [Rectangle(1,7), Rectangle(3, 4), Rectangle(5,2), Rectangle(2,6)] l.sort(cmp = cmp_width, reverse = True) for r in l: 3

print r 2 Sträng- och filhantering I de flesta P-uppgifter behöver man läsa och eventuellt skriva till fil. Filerna antas ha ett speciellt format som finns beskrivet i uppgiftslydelsen. Oftast läser man rad för rad från filen och använder sig av sträng-metoder för att få tag på de bitar som man behöver. Anta t ex att man har skrivit ett antal rektanglar till fil: -------------------- rects.txt -------------------- --------------------------------------------------- Om vi nu ska läsa filen och skapa rektanglar med angivet bredd och höjd kan vi göra på följande sätt: def read_rectangles(filename): # rad 1 f = open(filename, "r") # rad 2 rects = [] # rad 3 for line in f: # rad 4 wh = line.split() # rad 5 width = int(wh[0].split(":")[1]) # rad 6 height = int(wh[1].split(":")[1]) # rad 7 rects.append(rectangle(width, height)) # rad 8 return rects # rad 9 Givet funktionen ovan kan vi enkelt läsa in våra rektanglar från fil: l = read_rectangles("rects.txt") for r in l: print r 4

Några kommentarer behövs om read_rectangles. På rad 4 har vi en for-loop. För fil-objekt innebär det att vi loopar över innehållet rad för rad. Ett annat sätt att åstadkomma samma sak vore att byta ut rad 4 mot följande två rader: lines = f.readlines() for line in lines: På rad 5 använder vi sträng-metoden split. split är en väldigt användbar metod och det är värt att spendera lite tid åt att lära sig hur den fungerar. Om man anropar den utan några argument kommer man att få tillbaka en lista med delsträngar av den ursprungliga strängen. Strängen har splittats med hjälp av blanka tecken, det vill säga mellanslag, tab och nyrads-tecken. s = "hej san svej san" s.split() [ hej, san, svej, san ] s = "a-->b-->c-->def" s.split("-->") [ a, b, c, def ] Om man skickar en sträng som parameter kommer denna sträng att användas för att dela upp strängen: s = "hej, san, svej san" s.split(",") [ hej, san, svej san ] För att återgå till vårt exempel så kommer line att referera till strängen "" första varvet i for-loopen. På rad 5 kommer wh att vara listan [ w:3, h:4 ]. Och nu borde du själv kunna förstå vad rad 6 och 7 gör. 3 Exempeluppgift Anta nu att vi ska skriva ett program för att hantera information om bilar. För enklehets skull antar vi att det endast finns två saker vi ska hålla reda på för varje bil; färg och tillverkningsår. Vårt program ska kunna läsa information om bilar från en fil, skriva ut alla bilar sorterade på tillverkningsår och användaren ska kunna be om utskrift av alla bilar med en viss färg. Vi börjar med att skriva en klass Car. Instanser av Car ska ha två attribut: year och color. Dessutom ska vi skriva följande metoder: init, str och cmp. class Car(object): def init (self, year, color): self.year = year 5

self.color = color def str (self): return str(self.year) + "/" + str(self.color) def cmp (self, other): if self.year < other.year: return -1 if self.year > other.year: return 1 return 0 Nu skapar vi en klass Car_program som har i uppgift att läsa bilar från fil och hantera en lista med bilar. Vi kommer dessutom att låta den ha en dictionary med färger som nyckel och lista med bilar som värden. class Car_program(object): def init (self, filename): self.car_list = [] self.color_dict = {} self.read_file(filename) self.setup_dict() def read_file(self, filename): f = open(filename, "r") for line in f: attributes = line.split("/") year = int(attributes[0]) color = attributes[1].strip() self.car_list.append(car(year, color)) def setup_dict(self): for c in self.car_list: l = self.color_dict.get(c.color, []) l.append(c) self.color_dict[c.color] = l Vi har antagit att filen vi läser har följande format: -------------------- cars.txt -------------------- 2003/blue 1987/black 2006/red 1993/black 2002/blue 2001/green -------------------------------------------------- 6

Det mesta av koden borde vara bekant vid det här laget. Det kan vara värt att kommentera andra raden i metoden setup_dict. Jag har använt dictmetoden get. Om man försöker slå upp i en dictionary med en nyckel som inte finns kommer det att uppstå ett exception. Med get-metoden kan man instället tala om vad som kommer att returneras om nyckeln inte finns. I vårt fall har vi sagt om en viss färg inte finns i vår dictionary så ska en tom lista returneras. Observera att jag inte har skrivit kod för interaktion med användaren och jag kommer heller inte att skriva huvudprogrammet. Det viktiga nu är att inse att det mesta av jobbet är gjort. Vill man till exempel skriva ut alla bilar sorterade efter år kan man göra följande: prog = Car_program("cars.txt") prog.car_list.sort() for c in prog.car_list: print c 1987/black 1993/black 2001/green 2002/blue 2003/blue 2006/red Och vill man skriva ut alla bilar med en viss färg gör man så här: for c in prog.color_dict["black"]: print c 1987/black 1993/black for c in prog.color_dict["red"]: print c 2006/red Ett vanligt nybörjarmisstag är att lägga listan med alla bilar i klassen Car. Även om detta skulle fungera i små program så är det en dålig idé. Man vill att de datatyper man skapar ska vara så självständiga som möjligt. Det gör koden lättläst och det är lättare att lägga till och ändra ett programs beteende senare. Ett annat misstag är att försöka göra allt med en enda lista. Kom ihåg att variabler, listor och dicts endast refererar till objekt i minnet. Att vi sorterar car_list har till exempel ingen effekt på color_dict. Det är ju bara referenser till Car-objekten vi sorterar! Med andra ord, det går bra att ha samma objekt i flera datastrukturer. 7