TDDC76 - Programmering och Datastrukturer

Relevanta dokument
Objektorientering - Arv och polymorfi. Eric Elfving Institutionen för datavetenskap

TDDC76 - Programmering och Datastrukturer

TDDC76 - Programmering och Datastrukturer

Introduktion. Klasser. TDP004 Objektorienterad Programmering Fö 2 Objektorientering grunder

Innehåll. 1 Kort om dynamisk polymorfism. 2 Arv i C++ 3 Multipelt arv. 4 Något om statisk polymorfism. class Container {

TDDC76 Programmering och datastrukturer

Introduktion till arv

Programmering i C++ EDA623 Arv. EDA623 (Föreläsning 6) HT / 42

Innehåll. Pekaren this Självreferens. Klasser Resurshantering, representation. Överlagring av operatorer. Överlagring av operatorer

Dynamisk bindning och polymorfism

Programsystem konstruktion med C++ (2D1387) Innehåll. övning 2 klasser och arv

C++ Objektorientering - Klasser. Eric Elfving

TDDC76 - Programmering och Datastrukturer

TDDC76 - Programmering och Datastrukturer

Objektorientering - Arv och polymorfi

TDIU01 - Programmering i C++, grundkurs

TDDC76 - Programmering och Datastrukturer

TENTAMEN CD5250. Objektorienterad programutveckling med C++, 5p. Datum: , Tid: 14:00-19:00

TDIU01 Programmering i C++

Innehåll. Konstruktorer vid arv Regler för basklassens konstruktor. Konstruktorer vid arv. Konstruktorer vid arv. Konstruktorer vid arv

Övningar Dag 2 En första klass

Del3 Klassanvändning, operatorer och pekare Ämnesområden denna föreläsning:

Kapitel 3. Synlighet. Kapitel 3 - Klassanvändning, operatorer och pekare. Synlighet

TDIU20 - Objektorienterad programmering i c++ - föreläsning 6

Synlighet. Namespace Scope-operatorn Klasser Vänner

5 Arv och dynamisk bindning FIGUR

C++ Objektorientering - Klasser. Eric Elfving Institutionen för datavetenskap

TDIU01 - Programmering i C++, grundkurs

Del2 Klasser, medlemmar och arv Ämnesområden denna föreläsning:

TDP004. Minne och pekare. Eric Elfving Institutionen för datavetenskap

Arv. Objektorienterad och komponentbaserad programmering

Innehåll. Pekare Exempel

Programmering i C++ EDA623 Objektorienterad programutveckling. EDA623 (Föreläsning 5) HT / 33

Polymorfi. Objektorienterad och komponentbaserad programmering

Innehåll. Pekare Exempel

Introduktion. Lagom är bäst. OO eller ej? TDP004 Objektorienterad Programmering Fö 7 Objektorienterad design, tips och råd

Objektorienterade programmeringsspråk. Objektorienterade språk. Den objekt-orienterade modellen. Jämför med icke-oo

Klasshierarkier - repetition

Idag. statiska metoder och variabler. private/public/protected. final, abstrakta klasser, gränssnitt, delegering. wrapper classes

Objektorienterad programmering Föreläsning 12. Copyright Mahmud Al Hakim

Static vs Dynamic binding Polymorfism. Objekt-orienterad programmering och design (DIT953) Niklas Broberg, 2018

Tentamen i TDP004 Objektorienterad Programmering Lösningsförslag

Tentamen i TDP004 Objektorienterad Programmering Teoretisk del

UML. Klassdiagr. Abstraktion. Relationer. Överskugg. Överlagr. Aktivitetsdiagram Typomv. Typomv. Klassdiagr. Abstraktion. Relationer.

OOP Objekt-orienterad programmering

DD2387 Programsystemkonstruktion med C++ Tentamen 2

Föreläsning 8 - del 2: Objektorienterad programmering - avancerat

Klasser. Det är egentligen nu som kursen i programmeringsteknik börjar..., s k objektorienterad programmering.

Static vs Dynamic binding Override vs Overload. Objekt-orienterad programmering och design Alex Gerdes och Sólrún Halla Einarsdóttir, 2018

2I1049 Föreläsning 5. Objektorientering. Objektorientering. Klasserna ordnas i en hierarki som motsvarar deras inbördes ordning

Programsystemkonstruktion med C++: Övning 2. Karl Palmskog september 2010

Klasser. Kapitel 2. Kapitel 2 - Klasser, medlemmar och arv. Klasser. Klasser Medlemmar Arv

Problemet. Vi har sett att vi kan ersätta de metoder vi ärver från överklassen med egen funktionalitet (polymorfism)

Tillämpad programmering

Outline. Objektorienterad Programmering (TDDC77) Att instansiera en klass. Objekt. Instansiering. Åtkomst. Abstrakt datatyp.

Static vs Dynamic binding Polymorfism. Objekt-orienterad programmering och design Alex Gerdes, 2016

Tentamen i TDP004 Objektorienterad Programmering Praktisk del

Arv: Fordonsexempel. Arv. Arv: fordonsexempel (forts) Arv: Ett exempel. En klassdefinition class A extends B {... }

Programsystemkonstruktion med C++

F8 - Arv. ID1004 Objektorienterad programmering Fredrik Kilander

Outline. Objektorienterad Programmering (TDDC77) Signatur. Klassen calculator. Överlagring (overloading) Arv (inheritance) Ahmed Rezine

F8: Typkonvertering i C++

Högskolan Dalarna sid 1 av 5 Data-avdelningen Hans-Edy Mårtensson

KLASSER. Inkapsling Abstrakt datatyp Public och private. Klassmedlemmar Datamedlemmar Exempel Funktionsmedlemmar

Objektorienterad Programmering (TDDC77)

Vad är en klass? Övning 2. Konstruktorer. ffl copy-konstruktorn tar en instans av klassen som. ffl default-konstruktorn tar inga argument och kan

SMD091 Lektion 9. Definition. Inkapsling. Lite repetition. Grafik. Gränssnitt Definition och Implementation. Sammansättning... Implementation.

TDDC30. Objektorienterad programmering i Java, datastrukturer och algoritmer. Föreläsning 2 Jonas Lindgren, Institutionen för Datavetenskap, LiU

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

Imperativ programmering. Föreläsning 4

Föreläsning 5-6 Innehåll

Programmering i C++ EDA623 Mer om klasser. EDA623 (Föreläsning 6) HT / 26

Tentamen EDAF30 Programmering i C++

Kopiering av objekt i Java

Skapa, kopiera och destruera klassobjekt

Tentamen. Programmeringsmetodik, KV: Java och OOP. 17 januari 2002

Objektorienterad Programmering (TDDC77)

Arv bakgrund (kap. 9)

Ett objekt... Exempel: Om ni tittar er runt i föreläsningssalen ser in många olika fysiska föremål:

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

DD2387 Programsystemkonstruktion med C++ Tentamen 1 Torsdag 7 januari 2016, 14:00-18:00

Innehåll. Användardefinierade typer. Användardefinierade typer Kategorier. Konstruktorer. Konstruktorer Två sätt att skriva initiering av medlemmar

Föreläsning 13 Innehåll

Innehåll. Typomvandlingar (casting) Implicita Typomvandlingar. Typomvandlingar (type casts) Explicita, namngivna typomvandlingar (C++-11)

Det objektorienterade synsättet. Objekt. Datorprogrammet kan uppfattas som en slags modell av den verklighet programmet skall samverka med.

Exempel på användning av arv: Geometriska figurer

TDDC30. Objektorienterad programmering i Java, datastrukturer och algoritmer. Föreläsning 4 Erik Nilsson, Institutionen för Datavetenskap, LiU

Innehåll. Introduktion till objektorientering. OOP (objektorienterad programmering) Objekt, instanser, klasser

Målen med OOSU. Objektorienterad programmering. Objektorienterad programmering. Karlstads Universitet, Johan Öfverberg 1

TDDE10 m.fl. Objektorienterad programmering i Java Föreläsning 6 Erik Nilsson, Institutionen för Datavetenskap, LiU

Innehåll. dynamisk bindning. och programmering CRC) u Arv, polymorfi och

Classes och Interfaces, Objects och References, Initialization

JUnit. Ska kompletteras med kodexempel på JUnit. DD2385 Programutvecklingsteknik Några bilder till föreläsning 12 21/5 2012

ID1004 Laboration 3, 5-6 November 2012

Objektorienterad Programkonstruktion, DD1346 FACIT. Tentamen , kl

Objekt-orienterad programmering. Klassbegreppet och C++ UML. UMLs fördelar

Objektorienterad programmering i Java, datastrukturer och algoritmer. Föreläsning 4 Jonas Lindgren, Institutionen för Datavetenskap, LiU

Tillämpad programmering

Arv och polymorfism i Java

Transkript:

TDDC76 - Programmering och Datastrukturer Objektorientering - Arv och polymorfi Eric Elfving Institutionen för datavetenskap

1 / 25 Med hjälp av arv kan vi bryta ut saker som är gemensamt hos flera klasser. Vi får också möjlighet att referera till en grupp av klasser. Vi studerar ett par exempel:

2 / 25 Listing 1: Rectangle.h class Rectangle public: Rectangle(double h, double w) : heighth, widthw double area() const return height * width; double get_height() const return height; double get_width() const return width; private: double height; double width; ; Listing 2: Triangle.h class Triangle public: Triangle(double h, double w) : heighth, widthw double area() const return height * width / 2.0; double get_height() const return height; double get_width() const return width; private: double height; double width; ;

3 / 25 De två klasserna är helt olika typer, men har väldigt mycket gemensamt. Upprepning av kod bör undvikas - ger risk för buggar I C++ (och alla andra objektorienterade språk) kan vi skapa en gemensam basklass som får hantera de delar som klasserna delar.

4 / 25 Listing 3: Shape.h class Shape public: Shape(double width, double height) : widthwidth, heightheight double get_height() const return height; double get_width() const return width; private: double width; double height; ;

5 / 25 Sedan låter vi Rectange och Triangle ärva från Shape: Listing 4: Rectangle.h class Rectangle: public Shape public: Rectangle(double h, double w) : Shapew,h double area() const return height * width; ; Listing 5: Triangle.h class Triangle : public Shape public: Triangle(double h, double w) : Shapew,h double area() const return height * width / 2.0; ;

6 / 25 Detta fungerar dock inte! Triangle.h: In member function double Triangle::area() const : Triangle.h:10:16: error: double Shape::height is private within this context return height * width / 2.0; ^~~~~~ In file included from Triangle.h:1:0: Shape.h:17:12: note: declared private here double height; ^~~~~~

6 / 25 Detta fungerar dock inte! Triangle.h: In member function double Triangle::area() const : Triangle.h:10:16: error: double Shape::height is private within this context return height * width / 2.0; ^~~~~~ In file included from Triangle.h:1:0: Shape.h:17:12: note: declared private here double height; ^~~~~~ Medlemmarna är deklarerade som privata i Shape!

7 / 25 Rectangle är en Shape. Vi kan anropa de publika medlemsfunktionerna i Shape som om de vore våra: Listing 6: Rectangle.h class Rectangle: public Shape public: Rectangle(double h, double w) : Shapew,h double area() const return get_height() * get_width(); ;

8 / 25 Hittills har vi använt medlemsåtkomst public och private. Det finns också en tredje variant, protected vilket gör medlemmar tillgängliga som om de vore publika från subklasser men privata i övrigt. Det är viktigt att alltid fundera på gränssnittet hos en klass - vilka medlemmar ska vi ge tillgång till och till "vem"?

9 / 25 Listing 7: Shape.h class Shape public: Shape(double width, double height) : widthwidth, heightheight double get_height() const return height; double get_width() const return width; protected: double width; double height; ; Nu kommer vi åt dem som om de vore deklarerade direkt i vår subklass!

10 / 25 Utifrån kommer vi åt de publika medlemmarna från båda klasserna: int main() Triangle t12,4; cout << t.get_height() << " " << t.area() << endl;

11 / 25 Om vi skapar en funktion som tar emot en referens till Shape kan vi även skicka in Triangle och Rectangle void foo(shape const & s) cout << s.get_height() << endl; int main() Triangle t12,4; foo(t);

12 / 25 Problemet är att vi endast når saker som finns publikt i Shape. Hur får vi reda på arean?

13 / 25 Polymorfi! Med nyckelordet virtual kan vi deklarera en medlem i en basklass som subklasser kan skriva över. class Shape public: //... virtual double area() const; protected: double width; double height; ; Listing 8: Shape.h

14 / 25 Vi behöver inte göra någon ändring i subklasserna, men lägger vi till override kommer kompilatorn kontrollera att vi inte råkat skapa en ny funktion (dvs en överlagring). class Rectangle: public Shape public: Rectangle(double h, double w) : Shapew,h double area() const override return width * height; ; Listing 9: Rectangle.h

15 / 25 Detta kommer dock inte kompilera -- vi måste implementera Shape::area! Frågan är hur vi gör det?

16 / 25 Vi kan säga till kompilatorn att vi inte vill implemetera en virtuell funktion, den kallas då pure virtual" Klassen kallas då abstrakt - vi kan inte skapa objekt av den typen. Subklasser måste implementera funktionen för att även de inte ska vara abstrakta class Shape //... virtual double area() const = 0; //... ;

17 / 25 void foo(shape const & s) cout << s.area() << endl; int main() Triangle t12,4; foo(t); // Shape s12,3; // Inte tillåtet, Shape är abstrakt

För att få tillgång till polymorfi krävs två saker i C++: En referens (eller pekare) till basklass Anrop till en virtuell funktion 18 / 25

19 / 25 I C++ brukar man tala om ett uttrycks statiska och dynamiska typ. Antag följande deklaration: Triangle t12,5; Shape & s t ; Den statiska typen av s är alltid Shape & Den dynamiska typen beror på vad s refererar till, i detta fall Triangle

När vi anropar en medlemsfunktion kommer kompilatorn göra följande: Om funktionen inte är virtuell Anropa funktionen hos den statiska typen Annars, om funktionen är virtuell och den statiska typen är av pekare- eller referenstyp Anropa funktionen hos den dynamiska typen 20 / 25

Hittills har vi jobbat med referenser till basklass. Detta fungerar ofta bra, men vi har såklart problem: Vi måste initiera en referens med en existerande variabel Vi kan aldrig ändra på en referens 21 / 25

22 / 25 Ofta används istället pekare: int main() Shape * s; s = new Triangle4,7; cout << s->area() << endl;

23 / 25 Problemet är så klart de vanliga pekarproblemen: Minnesläckor Avreferera felaktiga adresser... På måndag diskuterar vi några hjälpmedel (smartpekare)

24 / 25 Även om vi kommer ihåg att köra delete kommer vi få problem... int main() Shape * s; s = new Triangle4,7; cout << s->area() << endl; delete s;

24 / 25 Även om vi kommer ihåg att köra delete kommer vi få problem... int main() Shape * s; s = new Triangle4,7; cout << s->area() << endl; delete s; Destruktorn är inte virtuell

24 / 25 Även om vi kommer ihåg att köra delete kommer vi få problem... int main() Shape * s; s = new Triangle4,7; cout << s->area() << endl; delete s; Destruktorn är inte virtuell endast basklassens destruktor körs

25 / 25 Vi har ingen speciell resurs att hantera här - den automatgenererade destruktorn fungerar bra. Markera den som = default class Shape //... virtual ~Shape() = default; //... ; Vi har även tillgång till = delete om vi vill förbjuda användning av (och generering av) vissa funktioner.

Eric Elfving Institutionen för datavetenskap www.liu.se