1 / 19

Data Structures - CSCI 102

Data Structures - CSCI 102. CS102. C++ Polymorphism. Prof Tejada. 1. Data Structures - CSCI 102 Polymorphism What is polymorphism ? The ability of an object of one type to appear and be used like an object of a different type Remember our Shape and Triangle classes?

bona
Download Presentation

Data Structures - CSCI 102

An Image/Link below is provided (as is) to download presentation Download Policy: Content on the Website is provided to you AS IS for your information and personal use and may not be sold / licensed / shared on other websites without getting consent from its author. Content is provided to you AS IS for your information and personal use only. Download presentation by click this link. While downloading, if for some reason you are not able to download a presentation, the publisher may have deleted the file from their server. During download, if you can't get a presentation, the file might be deleted by the publisher.

E N D

Presentation Transcript


  1. DataStructures-CSCI102 CS102 C++Polymorphism Prof Tejada 1

  2. DataStructures-CSCI102 Polymorphism Whatispolymorphism? Theabilityofanobjectofonetypetoappearandbe usedlikeanobjectofadifferenttype RememberourShapeandTriangleclasses? Basedoninheritance,TriangeIs-AShapeso... WecanactuallypassTrianglesaroundasShapes! Trianglet(5,5,15,20); Shapetval=t; Shape&tref=t; Shape*tptr=&t; Shape*tptr2=newTriangle(1,2,55,62); Youcanwriteveryadvancedcodewithpolymorphism Writealgorithms&frameworksthatmanipulatebaseclass Canevenwritecodeforsubclassesthathasn’t beenrealizedordesigned! 3

  3. DataStructures-CSCI102 Polymorphism Sowhatdoesthiscodedo? Trianglet(5,5,15,20); t.print(); Shapetval=t; tval.print(); Shape&tref=t; tref.print(); Shape*tptr=&t; tptr->print(); ItshouldcalltheTriangleobject’soverloadedprintmethod, right?Doesit? 4

  4. DataStructures-CSCI102 Early/Static/Compile-TimeBinding EventhoughwecanpassaroundaTriangleasaShape,it doesn’thelpifwecan’tmakeitcallTriangle’soverloaded methods Whydoesthishappen? Whenyourcodeiscompiled,thecompilerdirectly associatesafunctioncallwithamemorylocationto makefunctioncallsafastlookup Whenyoucompilersees"s.print()",itimmediately associatesitwiththeShapeclass Isn’ttheresomewaytotellthecompilertowaituntil run-timetofigureoutwhatversionofthe"print()"function itshouldcall? 5

  5. DataStructures-CSCI102 VirtualFunctions TellstheC++towaituntilthecoderunstofigureoutwhat versionofamethoditshouldactuallycall ThekeywordvirtualtellsC++tofindthe"most-derived" versionofamethod(a.k.a.theonefarthestdownthe inheritancetreethat’sstillrelevant) Howisitused? Justaddthekeywordvirtualtothebeginningofany functionprototypeinyourclass Technically,youonlyhavetoaddvirtualtothe superclassmethod,butit’sgoodstyleifyouaddittoall ofthefunctionsthatareaffectedbyit Whynotjustdeclareeveryfunctionvirtual? It’smoreexpensivethannormallookup(time& space) 6

  6. DataStructures-CSCI102 VirtualFunctions Beforewehadthis: classShape{ ... voidprint()const; }; Nowwehavethisinstead: classShape{ ... virtualvoidprint()const; }; 7

  7. DataStructures-CSCI102 Late/Dynamic/Run-TimeBinding Howdoesthevirtualkeywordactuallywork? IttellsC++thatit’snotpossibletoknowwhatversionof thatparticularfunctiontocalluntilrun-time Thecompilerconstructsavirtualtableforeveryclass thathasavirtualfunction Eachoftheseclassesstoresahiddenpointertoitsown virtualtable Thevirtualtableprovidesarun-timelookupforeach classtoknowwhatversionoffunctionstocallusing functionpointers 8

  8. DataStructures-CSCI102 Other"Virtual"Details Ifyou’reusinginheritance,youshouldALWAYSmakeyour baseclass’Destructorvirtual Ifyoudon’tC++willonlycallthesuperclassdestructor andwillskipyoursubclassdestructor Dynamicbindingonlyworksforreferencesandpointers!!! Trianglet(5,5,15,20); t.print(); Shapetval=t; tval.print();//callsShape’sprint()!!! Shape&tref=t; tref.print();//callsTriangle’sprint() Shape*tptr=&t; tptr->print();//callsTriangle’sprint() 9

  9. DataStructures-CSCI102 Polymorphism Whyispolymorphismuseful? Allowsyoutoreusealotofcodethatworksforsimilar objects Allowsyoutoaddnewclassestoyourinheritance hierarchy,butallyourexistingmethodswillstillwork justfine! Whatifweaddanewsubclassof"Shape"? Allowsyoutoconstructverysophisticatedcodethatis simple,butpowerful 10

  10. DataStructures-CSCI102 PureVirtualFunctions Whatifthere’safunctionthatthesuperclasscan’tdefine, butweneedthesubclassestodefine? classShape{ virtualdoublegetArea()const; }; TheproblemhereisthatShapehasnodetailsabouthowto calculateanarea.Ourfunctionwouldenduplooking somethinglikethis(notveryuseful): doubleShape::getArea()const {return0;} 11

  11. DataStructures-CSCI102 PureVirtualFunctions ThegetArea()functionisnotmeaningfulforShape,butitis meaningfulforallsubclassesofShape NeedtomakegetArea()asapurevirtualfunction ShapedoesnotneedtoimplementgetArea() Allsubclassesofshapeshouldbeforcedtoimplementa definitionofgetArea() classShape{ virtualdoublegetArea()const=0; }; 12

  12. DataStructures-CSCI102 AbstractBaseClasses Whataretheconsequencesofmakingafunctioninaclass apurevirtualfunction? IfShapecontainsapurevirtualfunction,itcannolonger beinstantiated! WhatwouldhappenifyoumadeaShapeobjectand triedtocallgetArea()? Shapebecomesanabstractbaseclass AnysubclassofShapethatdoesn’timplementareal versionofgetArea()alsobecomesanabstractbaseclass! Ifyouwanttouseyourderivedclasses,youMUST overridethegetArea()method 13

  13. DataStructures-CSCI102 PolymorphicPrintFunction Hereisanexampleofafunctionthatisimplementedusing polymorphismtomaintainflexibility: voidprintArea(constShape&s) { cout<<"Area="<<s.getArea()<<endl; } WhatifwedecidetoaddanothersubclasslikeRectangleto ourexistinginheritancehierarchy? Youwon’tneedtochangeprintArea()! 14

  14. DataStructures-CSCI102 InterfaceClasses Usingtheideasofpurevirtualfunctionsandabstractbase classesyoucouldcreateaclassthathasno implementationatall! Aninterfaceclassisaclassthatcontainsonlypurevirtual functions Veryusefulforwhenyouwanttotellsubclasseswhat functionstheymustprovide,butyoudon’twantto influencetheirimplementation It’sabetter/saferwaytodomultipleinheritance(Java andC#actuallysplitinterfaceout) Actually,itisTHErightwaytodomultipleinheritance InterfaceclassesusuallyprefixtheirnamewithI e.g."Shape"wouldbecome"IShape" 15

  15. DataStructures-CSCI102 polymorph_point.h #ifndefPOLYMORPH_POINT_H_ #definePOLYMORPH_POINT_H_ #include<iostream> classPoint { private: intx; inty; public: Point(intnewx,intnewy):x(newx),y(newy){} virtual~Point(){}//Avirtualdestructor intgetX()const{return intgetY()const{return voidsetX(intnewx){x= voidsetY(intnewy){y= x;} y;} newx;} newy;} friendstd::ostream&operator<<(std::ostream&out, constPoint&b); }; std::ostream&operator<<(std::ostream&out,constPoint&b) { out<<"("<<b.x<<","<<b.y<<")"; returnout; } #endif/*POLYMORPH_POINT_H_*/ 17

  16. DataStructures-CSCI102 polymorph_shape.h #ifndefPOLYMORPH_SHAPE_H_ #definePOLYMORPH_SHAPE_H_ #include"polymorph_point.h" classShape { protected: Pointcenter; public: Shape(intx,inty) :center(x,y) {} //Avirtualdestructor virtual~Shape(){} PointgetCenter()const{returncenter;} voidsetCenter(Pointp){center=p;} //Avirtualprintfunction virtualvoidprint()const { std::cout<<"Shapelocatedat"<<center<<std::endl; } //Apurevirtualareacalculationfunction virtualdoublegetArea()const=0; }; #endif/*POLYMORPH_SHAPE_H_*/ 18

  17. DataStructures-CSCI102 polymorph_triangle.h #ifndefPOLYMORPH_TRIANGLE_H_ #definePOLYMORPH_TRIANGLE_H_ #include"polymorph_point.h" #include"polymorph_shape.h" classTriangle:publicShape { private: intbase; intheight; public: Triangle(intb,inth,intx,inty):Shape(x,y) {base=b;height=h;} intgetBase()const{ intgetHeight()const voidsetBase(intb){ voidsetHeight(inth) returnbase;} {returnheight;} base=b;} {height=h;} virtualvoidprint()const {std::cout<<"Trianglelocatedat"<<center <<std::endl;} virtualdoublegetArea()const {return(.5*base*height);} }; #endif/*POLYMORPH_TRIANGLE_H_*/ 19

  18. DataStructures-CSCI102 polymorph_rectangle.h #ifndefPOLYMORPH_RECTANGLE_H_ #definePOLYMORPH_RECTANGLE_H_ #include"polymorph_point.h" #include"polymorph_shape.h" classRectangle:publicShape { private: intwidth; intheight; public: Rectangle(intw,inth,intx,inty):Shape(x,y) {width=w;height=h;} intgetWidth()const{returnwidth;} intgetHeight()const{returnheight;} voidsetBase(intw){width=w;} voidsetHeight(inth){height=h;} virtualvoidprint()const {std::cout<<"Rectanglelocatedat"<<center <<std::endl;} virtualdoublegetArea()const {return(width*height);} }; #endif/*POLYMORPH_RECTANGLE_H_*/ 20

  19. DataStructures-CSCI102 polymorph_main.cpp #include<iostream> #include<string> #include #include #include #include "polymorph_point.h" "polymorph_shape.h" "polymorph_triangle.h" "polymorph_rectangle.h" usingnamespacestd; voidprintArea(constShape&s) { cout<<"Areaofshapeis"<<s.getArea()<<endl; } intmain() { Triangle*t=newTriangle(10,10,10,10); printArea(*t); deletet; Rectangle*r=newRectangle(10,15,20,25); printArea(*r); deleter; } 22

More Related