• Like
3d7b7 session4 c++
Upcoming SlideShare
Loading in...5
×

3d7b7 session4 c++

  • 505 views
Uploaded on

 

More in: Technology , Business
  • Full Name Full Name Comment goes here.
    Are you sure you want to
    Your message goes here
    Be the first to comment
    Be the first to like this
No Downloads

Views

Total Views
505
On Slideshare
0
From Embeds
0
Number of Embeds
0

Actions

Shares
Downloads
17
Comments
0
Likes
0

Embeds 0

No embeds

Report content

Flagged as inappropriate Flag as inappropriate
Flag as inappropriate

Select your reason for flagging this presentation as inappropriate.

Cancel
    No notes for slide
  • Amity Business School

Transcript

  • 1. Course Name- B Sc IT Subject Name - C++ Semester - II Neetu Gupta1
  • 2. Contents• Function overloading• Operator overloading• Inheritance• Different forms of inheritance• Constructors and• Destructors in inheritance• Virtual base class
  • 3. Contents• Virtual base class• Pointer to base class• Dynamic polymorphism• Virtual functions• Type conversions
  • 4. Function overloading• In C we can have only one function with a given name.• But, in C++ we have a feature to declare more than one function with the same name as long as they have different signatures i.e. parameters.• The difference in parameters could be either in number or type or both.
  • 5. • Function overloading is the practice of declaring the same function with different signatures.• The same function name will be used with different number of parameters and parameters of different type. But overloading of functions with different return types are not allowed.• You overload a function name f by declaring more than one function with the name f in the same scope. The declarations of f must differ from each other by the types and/or the number of arguments in the argument list.
  • 6. • For examples we can have following functions in a c++ program void Add(int x, int y) { cout<<" Integer addition result: "<<(x+y); } void Add(double x, double y) { cout<< " Double addition result: "<<(x+y); } void Add(float x, float y) { cout<< " float addition result: "<<(x+y); }Three functions with same name i.e. Add(..) but differ in types
  • 7. Calling an overloaded function• When we call an overloaded function, the correct function is selected by comparing the argument list of the function call with the parameter list of each of the overloaded functions.• The function i.e. actually called depends upon the arguments we pass at the time of function call statement.• This is an example of static polymorphism
  • 8. int main() { Add (10,10); Add (10.10d, 10.5d); Add (10.10f, 10.5f);}• Add (10,10); calls the function void Add (int x, int y)• Add (10.10d, 10.5d); calls the function void Add (double x, double y)• Add (10.10f, 10.5f); calls the function void Add (float x, float y)
  • 9. • Remember function overloaded can not be done on the basis of return type.• For example following functions will give error, as both the functions are same as they only differ in return type: void Add(int x, int y) int Add(int x, int y)
  • 10. Operator overloading• C++ CVectororporates the option to use standard operators to perform operations with classes in addition to with fundamental types.For example, int a, b, c; a = b + c;• This is obviously valid code in C++, sCVectore the different variables of the addition are all fundamental types.
  • 11. • But if we have a code like• class Product { string name; float price; }; Product prod1, prod2, prod3; prod3 = prod1 + prod2; // Compilation error• The above code will not work, as the compiler does not on how to apply + on Product type variables i.e. prod1 and prod2 here.
  • 12. • Using C++ feature to overload operators, we can design classes able to perform operations using standard operators.• Here is a list of all the operators that can be overloaded: + - * / = < > += -= *= /= << >> <<= >>= == != <= >= ++ -- %&^!|~ &= ^= |= && || %= [] () , -> * -> new delete new[] delete[]
  • 13. • To overload an operator in order to use it with classes we declare operator functions, which are regular functions whose names are the operator keyword followed by the operator sign that we want to overload.• The format is will be as: type operator sign (parameters) { /*...*/ }
  • 14. • Example#CVectorlude <iostream>using namespace std;class CVector { public: int x, y; CVector () {}; // default constructor CVector (int,int); // constructor CVector operator + (CVector); // + operator overloaded};CVector: CVector (int a, int b) { x = a; y = b;}CVector CVector::operator+ (CVector param) { CVector temp; temp.x = x + param.x; temp.y = y + param.y; return (temp);}
  • 15. Here you have an example that overloads theaddition operator (+).• We are going to create a class to store bidimensional vectors• X represents x-coordinate and y represents y- coordinate value for a CVector.• The addition of two bidimensional vectors is an operation as simple as adding the two x coordinates to obtain the resulting x coordinate and adding the two y coordinates to obtain the resulting y.
  • 16. • Now see how can we use the class CVector as int main () { CVector a (3,1); CVector b (1,2); CVector c; c = a + b; cout << c.x << "," << c.y; return 0;}
  • 17. • Notice the below two methods CVector (int, int); // function name CVector (constructor) CVector operator+ (CVector); // function returns a CVector• The function operator+ of class CVector is the one that is in charge of overloading the addition operator (+).• This function of class CVector can be called either implicitly using the operator, or explicitly using the function name
  • 18. c = a + b; // using the operatorc = a.operator+ (b); // using the function name• Both these expressions are equivalent and will call the +operator function defined in class CVector.• This way we can overload any binary operator in c++ like - , /, % etc.
  • 19. Unary operator overloadingWe can overload unary operator using two ways as• with either a nonstatic member function that has no parameters return_type operator@()• Or with a nonmember function that has one parameter return_type operator@(T)Here,@ could be any unary opeartor and T is a type.return_type could be any type
  • 20. Add the following function to class CVector declared before CVector CVector::operator! () { CVector temp; temp.x = !x; temp.y = !y; return (temp); }Here operator ! Is overloaded and define a behavior for class CVector.
  • 21. The above code can be use in main() function asint main() { CVector ox(10,30); CVector oy = !ox // function operator! Is called}
  • 22. • Overloading decrement (--) and CVectorrement(++) operators is different• SCVectore ++ and – have different meanings for postfix and prefix we should override both forms.• For this we should add two set of functions like // Operator Function Definition for prefix type operator ++ (); type operator -- ();
  • 23. // Operator Function Definition for postfix type operator ++ (int); type operator -- (int);Here we make use of a dummy argument.• As you can see in this case we use int as a dummy argument for post-fix, when we redefine the functions for the unary CVectorrement (++) and decrement (--) overloaded operators.• You must remember that int isnt an integer, but just a dummy argument. You can see it as a signal to the compiler to create the post-fix notation of the operator.
  • 24. • Two functions for ++ operator in class CVector could be as below: CVector operator ++ () { // Operator Function Definition for prefix return CVector (++x, ++y); } CVector operator ++ (int) { // Operator Function Definition with dummy //argument for postfix return CVector (x++, y++); }
  • 25. • Similarly, Two functions for -- operator in class CVector could be as below: CVector operator -- () { // Operator Function Definition for prefix return CVector(--x, --y); } CVector operator -- (int) { // Operator Function Definition with dummy //argument for postfix return CVector (x--, y--); }
  • 26. Remember• In operator overloading always remember:2. We can not change the precedence and associatively of operators even if we overload them in a class.3. Few operators can not be overloaded like : • scope resolution operator - :: • sizeof operator • Conditional operator (?:) • class member access operators (.,.*)
  • 27. Type conversion• Type Conversion is the process of converting one type into another.• In other words converting an expression of a given type into another is called type casting or conversion• There are two ways • Automatic Conversion otherwise called as Implicit Conversion • Type casting otherwise called as Explicit Conversion
  • 28. Implicit Type Conversion• This is automatic conversion, which is not done using any operator or function.• The value gets automatically converted to the specific type in which it is assigned.• Looking at the expression, the compiler automatically converts an expression of one type into another type
  • 29. • For example #include <iostream.h> void main() { short x=6000; int y; y=x; }• In the above example the data type short namely variable x is converted to int and is assigned to the integer variable y.
  • 30. • However, some type conversions are inherently unsafe, and if the compiler can detect that an unsafe conversion is being implicitly requested, it will issue a warning.• For example if we write the code as below int nValue = 3.14156; // implicit conversion to integer value 3Here the fractional part of the double value 3.14156 is dropped because int type can not support fractional values.
  • 31. • Because converting a double to an int usually causes data loss (making it unsafe), compilers such as Visual Studio Express 2005 will typically issue a warning.• Few unsafe automatic conversions could be – assigning unsigned variables to signed variables (and vice-versa), – assigning large integers (eg. a 4-byte long) to integer variables of a smaller size (eg. a 2- byte short).
  • 32. Explicit Conversion• Explicit conversion can be done using type cast operator and the general syntax for doing this is datatype (expression);• Here in the above datatype is the type which the programmer wants the expression to gets changed• This is called c++ style casting
  • 33. #include <iostream.h> void main() { int a; float b,c; cout<< “Enter the value of a:”; cin>>a; cout<< “n Enter the value of b:”; cin>>b; c = float(a)+b; cout<<”n The value of c is:”<<c; } Output is Enter the value of a: 10 Enter the value of b: 12.5 The value of c is: 22.5•
  • 34. • In the above program a is declared as integer and b and c are declared as float. In the type conversion statement namely c = float (a) + b;• The variable a of type integer is converted into float type and so the value 10 is converted as 10.0 and then is added with the float variable b with value 12.5 giving a resultant float variable c with value as 22.5
  • 35. Inheritance• Inheritance allows one data type to acquire properties of other data types.• Inheritance allows to create classes which are derived from other classes, so that they automatically include some of its "parents" members, plus its own.• The original class is called the base class and the new class created using base class is called derived class.
  • 36. • For example, we are going to suppose that we want to declare a series of classes that describe polygons like our CRectangle, or like CTriangle. They have certain common properties, such as both can be described by means of only two sides: height and base.• This could be represented in the world of classes with a class CPolygon from which we would derive the two other ones: CRectangle and CTriangle.• The class CPolygon would contain members that are common for both types of polygon. In our case: width and height. And CRectangle and CTriangle would be its derived classes, with specific features that are different from one type of polygon to the other.
  • 37. NEED FOR INHERITANCE• Capability to express the inheritance relationship-This ensures the closeness with the real world models.• Reusability-The advantage of reusability are: faster development time and easier maintenance.• Transitive nature of inheritance-If a class B inherits properties of another class A then all subclasses of B will automatically inherits the properties of A. This property is called transitive nature of inheritance.
  • 38. Syntax• In order to derive a class from another, we use a colon (:) in the declaration of the derived class using the following format: class derived_class_name: public base_class_name { /*...*/ };Here derived_class_name is the name of the derived class and base_class_name is the name of the class on which it is based.
  • 39. // Example derived classes#include <iostream>using namespace std;class CPolygon { protected: int width, height; public: void set_values (int a, int b) { width=a; height=b; }};class CRectangle: public CPolygon { public: int area () { return (width * height); }};class CTriangle: public CPolygon { public: int area () { return (width * height / 2); }};
  • 40. • We can use the above created classes as int main () { CRectangle rect; CTriangle trgl; rect.set_values (4,5); trgl.set_values (4,5); cout << rect.area() << “n”; cout << trgl.area() << “n”; return 0; }• The objects of the classes CRectangle and CTriangle each contain members inherited from CPolygon. These are: width, height and set_values().• That’s is why we are using these members in main() method on the objects of classes CRectangle and CTriangle.
  • 41. • In CPolygon Class we used protected access specifier• The protected access specifier is similar to private. Its only difference occurs in fact with inheritance.• When a class inherits from another one, the members of the derived class can access the protected members inherited from the base class, but not its private members.• Since we wanted width and height to be accessible from members of the derived classes CRectangle and CTriangle and not only by members of CPolygon, we have used protected access instead of private.
  • 42. • We can summarize the different access types according to who can access them in the following way: Access public protected Private members of the yes yes yes same class members of the yes yes no derived class not members yes no no • Here "not members" represent any access from outside the class, such as from main(), from another class or from a function.
  • 43. protected inheritance• So far we have code written like class B : public A {}This means that the class B is publicily derived from B.• We can specify protected derivation as well as class B : protected A {}• If we specify a more restrictive access level like protected, all public members of the base class are inherited as protected in the derived class.
  • 44. • For example, if we write the code as class CRectangle: protected CPolygon { ... }• Then the function set_values() defined public in CPolygon will become protected in class CRectangle and we can not write code like CRectangle rect; rect.set_values (4,5); // Error
  • 45. private inheritance• As we can have public and protected base class, we can also have private base class.• We can specify private derivation as well as class B : private A {}• If we specify a more restrictive access level like private, all public and protected members of the base class are inherited as private in the derived class.
  • 46. • For example, if we write the code as class CRectangle: private CPolygon { public: int area () { return (width * height); } };The above code will not compile, because• We are inheriting CPolygon as private base class, hence the protected members width & height become private
  • 47. Types of Inheritance• Single Inheritance - When a subclass inherits only from one base class,it is known as single inheritance.class B: public A {}
  • 48. • Multiple Inheritance - When a subclass inherits from multiple base classes, it is known as multiple inheritance.class C: public A, public B {}
  • 49. • Hierarchical Inheritance - When many sub classes inherits from a single base class,it is known as hierarchical inheritance.
  • 50. • Multilevel Inheritance - When a subclass inherits from a class that itself inherits from another class,it is known as multilevel inheritance.class B: public A {}class C : public B {}
  • 51. • Hybrid Inheritance - When a subclass inherits from multiple base classes and all of its base classes inherits from a single base class,this form of inheritance is known as hybrid inheritance.
  • 52. Constructors & inheritance• Suppose I have a class B derived from A as class B : public A { public: B () {}; B (int i) {}; }• If I create an object as B b;Then how the constructor of class A is called as we are creating the object of class B only?
  • 53. The rule is :• Whenever we create an object of derived class then constructor of base is called automatically even if we do not call them explicitly.• If we are using multilevel inheritance then the call to constructor is starting from the first base class till the most derived class.
  • 54. // Example class A { public: A () { cout << “In A’s Constructor n”; } } class B : public A { public: B () { cout << “In B’s Constructor n”; } } class C : public B { public: C () { cout << “In C’s Constructor n”; } }
  • 55. main() { C c;}Output will be In A’s Constructor In B’s Constructor In C’s ConstructorHere we are creating an object of class C, so the constructor of class A is called first, then B and then C.
  • 56. Destructor• Like constructor, destructor of base is called automatically when the object of derived class s destroyed or deleted or goes out of scope• But the destructors are called in reverse order of the constructor call.• The destructor of derived is called first, then of its base class and so on.
  • 57. // Example class A { public: A () { cout << “In A’s Constructor n”; } ~A () { cout << “In A’s Destructor n”; } } class B : public A { public: B () { cout << “In B’s Constructor n”; } ~B () { cout << “In B’s Destructor n”; } } class C : public B { public: C () { cout << “In C’s Constructor n”; } ~C () { cout << “In C’s Destructor n”; } }
  • 58. main() { C c;}Output will be In A’s Constructor In B’s Constructor In C’s Constructor In C’s Destructor In B’s Destructor In A’s Destructor
  • 59. Multiple inheritance and ambiguity• We can inherit a class form more than one class and call id multiple inheritance.• Consider a inheritance situation as below: A member - i B : public A C : public A member – i of A member – i of A D : public B,C member – I of A via B Member – I of A via C
  • 60. • Here, the class D is derived form B and C. And both B and C are derived from A.• That means we have two copy of class A in class D.• When we create an object of class D, there are two i of A, one instance via class B and other instance of i via class C.• If I write a code like: D d; d.i; // ErrorCompiler is not able to resolve i in D as it has its two instances.
  • 61. Virtual base class• Duplication of inherited members due to these multiple paths can be avoided by making the common base class as virtual base class while declaring the direct or intermediate base clases.• Like we can declare the A as virtual base class when we inherit the A in B and C
  • 62. // Example class A { public: int i; } class B : public virtual A { ……….. } class C : public virtual A { ……….. } class D : public C,D { ……….. }
  • 63. Virtual functions• Before understanding the virtual fucntions, lets take a look at polymorphism.• Pointers to base class – One of the key features of derived classes is that a pointer to a derived class is type-compatible with a pointer to its base class. Polymorphism is the art of taking advantage of this simple but powerful and versatile feature, that brings Object Oriented Methodologies to its full potential.
  • 64. // pointers to base class#include <iostream>using namespace std;class CPolygon { protected: int width, height; public: void set_values (int a, int b) { width=a; height=b; }};class CRectangle: public CPolygon { public: int area () { return (width * height); }};class CTriangle: public CPolygon { public: int area () { return (width * height / 2); }};
  • 65. int main () { CRectangle rect; CTriangle trgl; CPolygon * ppoly1 = &rect; CPolygon * ppoly2 = &trgl; ppoly1->set_values (4,5); ppoly2->set_values (4,5); cout << rect.area() << endl; cout << trgl.area() << endl; return 0;}• In function main, we create two pointers that point to objects of class CPolygon (ppoly1 and ppoly2). Then we assign references to rect and trgl to these pointers, and because both are objects of classes derived from CPolygon, both are valid assignment operations.
  • 66. • The only limitation in using *ppoly1 and *ppoly2 instead of rect and trgl is that both *ppoly1 and *ppoly2 are of type CPolygon* and therefore we can only use these pointers to refer to the members that CRectangle and CTriangle inherit from CPolygon.• For that reason when we call the area() members at the end of the program we have had to use directly the objects rect and trgl instead of the pointers *ppoly1 and *ppoly2.• In order to use area() with the pointers to class CPolygon, this member should also have been declared in the class CPolygon, and not only in its derived classes, but the problem is that CRectangle and CTriangle implement different versions of area, therefore we cannot implement it in the base class. This is when virtual members become handy.
  • 67. Members declared as virtual• A member of a class that can be redefined in its derived classes is known as a virtual member.• In order to declare a member of a class as virtual, we must precede its declaration with the keyword virtual. virtual returntype function_name (parameters)
  • 68. // pointers to base class#include <iostream>using namespace std;class CPolygon { protected: int width, height; public: void set_values (int a, int b) { width=a; height=b; } virtual int area () { return (0); }};class CRectangle: public CPolygon { public: int area () { return (width * height); }};class CTriangle: public CPolygon { public: int area () { return (width * height / 2); }};
  • 69. • Now the three classes (CPolygon, CRectangle and CTriangle) have all the same members: width, height, set_values() and area(). int main () { CRectangle rect; CTriangle trgl; CPolygon poly; CPolygon * ppoly1 = &rect; CPolygon * ppoly2 = &trgl; CPolygon * ppoly3 = &poly; ppoly1->set_values (4,5); ppoly2->set_values (4,5); ppoly3->set_values (4,5); cout << ppoly1->area() << endl; cout << ppoly2->area() << endl; cout << ppoly3->area() << endl; return 0; }
  • 70. • The member function area() has been declared as virtual in the base class because it is later redefined in each derived class.• Now when we do the following CRectangle rect; CPolygon * ppoly1 = &rect; ppoly1->set_values (4,5); cout << ppoly1->area() << endl; Here the arear() method of appropriate class i.e. CRectangle is called because area() is declared as virtual in base class.• You can verify if you want that if you remove this virtual keyword from the declaration of area() within CPolygon, and then you run the program the result will be 0 for the three polygons instead of 20, 10 and 0.
  • 71. • That is because instead of calling the corresponding area() function for each object (CRectangle::area(), CTriangle::area() and CPolygon::area(), respectively), CPolygon::area() will be called in all cases since the calls are via a pointer whose type is CPolygon*.• Rule is: When a function is declared virtual in base class, then the function call via base class pointer is resolved at runtime and the function called is of the class whose object it is.
  • 72. • Therefore, what the virtual keyword does is to allow a member of a derived class with the same name as one in the base class to be appropriately called from a pointer, and more precisely when the type of the pointer is a pointer to the base class but is pointing to an object of the derived class, as in the above example.• A class that declares or inherits a virtual function is called a polymorphic class.• The resolving of function at runtime depending upon the type of object is called dynamic polymorphism.
  • 73. Abstract base class• Abstract base classes are something very similar to our CPolygon class of our previous example.• The only difference is that in our previous example we have defined a valid area() function with a minimal functionality for objects that were of class CPolygon (like the object poly),• whereas in an abstract base classes we could leave that area() member function without implementation at all.• This is done by appending =0 (equal to zero) to the function declaration.• An abstract base CPolygon class could look like this:
  • 74. // abstract class CPolygonclass CPolygon { protected: int width, height; public: void set_values (int a, int b) { width=a; height=b; } virtual int area () =0; };• Notice how we appended =0 to virtual int area () instead of specifying an implementation for the function. This type of function is called a pure virtual function, and all classes that contain at least one pure virtual function are abstract base classes.
  • 75. • Important : The main difference between an abstract base class and a regular polymorphic class is that because in abstract base classes at least one of its members lacks implementation we cannot create instances (objects) of it.• But a class that cannot instantiate objects is not totally useless. We can create pointers to it and take advantage of all its polymorphic abilities. Therefore a declaration like: CPolygon poly; would not be valid for the abstract base class we have just declared, because tries to instantiate an object. Nevertheless, the following pointers are valid: CPolygon * ppoly1; CPolygon * ppoly2;• This is so for as long as CPolygon includes a pure virtual function and therefore its an abstract base class. However, pointers to this abstract base class can be used to point to objects of derived classes.
  • 76. int main () { CRectangle rect; CTriangle trgl; CPolygon * ppoly1 = &rect; CPolygon * ppoly2 = &trgl; ppoly1->set_values (4,5); ppoly2->set_values (4,5); cout << ppoly1->area() << endl; cout << ppoly2->area() << endl; return 0;}• If you review the program you will notice that we refer to objects of different but related classes using a unique type of pointer (CPolygon*). This can be tremendously useful and called dynamic polymorphism.
  • 77. Thank You77