C++ Programming 상속과다형성 Seo, Doo-okok clickseo@gmail.com http://www.clickseo.com
목 차 상속의이해 상속과다형성 다중상속 2
상속과다형성 객체의이해 상속클래스의객체의생성및소멸 상속의조건 상속과다형성 다중상속 3
상속의이해 상속 (Inheritance) 클래스에구현된모든특성 ( 멤버변수와멤버함수 ) 을그대로계승받아 새로운클래스를만드는기능 기반클래스 (Base Class) : Super Class 파생클래스 (Derived class) : Sub Class class DerivedClass : public BaseClass // 자동으로기반클래스의멤버변수와함수를소유 // 새로운멤버변수와함수의추가가능 4
protected 멤버 상속의이해 이해 (cont d) 파생된클래스 ( 상속관계 ) 에서만접근을허용하는멤버 외부접근 : private 내부접근및상속관계 : public class BaseClass private: int a; protected: int b; class DerivedClass : public BaseClass void SetData(void) a = 10; // error b = 20; // 접근가능 int main(void) BaseClass base; // 외부접근 base.a a = 10; // error base.b = 20; // error return 0; 5
3 가지형태의상속 상속의이해 이해 (cont d) Base 클래스의멤버는 Derived 클래스로상속되는과정에서접근권한이변경된다. Base Class 상속형태 public 상속 protected 상속 private 상속 private 접근불가접근불가접근불가 protected protected protected private public public protected private class DerivedClass : public BaseClass class DerivedClass : protected BaseClass class DerivedClass : private BaseClass 6
프로그램예제 : public 상속 상속의이해 이해 (cont d) #include <iostream> class BaseClass private: int a; protected: int b; int c; class DerivedClass : public BaseClass void SetData(void) // a = 10; // error b = 20; c = 30; int main(void) DerivedClass c; // c.a = 10; // error // c.b = 20; // error c.c c = 30; return 0; 7
상속클래스의객체생성및소멸 상속클래스의객체생성과정 1. 메모리공간의할당 2. Base 클래스의생성자실행 3. Derived 클래스의생성자실행 BaseClass(); BaseClass DerivedClass DerivedClass(); 8
상속클래스의객체생성및소멸 (cont d) 프로그램예제 : 상속클래스의객체생성과정 #include <iostream> using std::cin; using std::cout; using std::endl; class BaseClass BaseClass() cout << "Base Class!!!" << endl; class DerivedClass : public BaseClass DerivedClass() cout << "DerivedClass Class!!!" << endl; int main() DerivedClass c; return 0; 9
상속클래스의객체생성및소멸 (cont d) 프로그램예제 : 상속과객체생성과정 (1/3) #include <iostream> #include <cstring> using std::cin; using std::cout; using std::endl; char name[12]; int age; Person Person(); const char GetName() const; int GetAge() const; class Person char name[12]; int age; Student Person(char *name = "", int age = 0) char major[50]; this->age = age; strcpy(this->name, name); Student(); const char *GetMajor() const; void ShowData() const; const char *GetName(void) const return name; int GetAge(void) const return age; 10
상속클래스의객체생성및소멸 (cont d) 프로그램예제 : 상속과객체생성과정 (2/3) class Student : public Person char major[50]; Student(char *name, int age, char *major) : Person(name, age) // this->age = age; // error // strcpy(this->name, name); // error strcpy(this->major, major); const char *GetMajor(void) const return major; void ShowData(void) const cout << " 이름 : " << GetName() << endl; cout << " 나이 : " << GetAge() << endl; cout << " 전공 : " << GetMajor() << endl; 11
상속클래스의객체생성및소멸 (cont d) 프로그램예제 : 상속과객체생성과정 (3/3) int main() Student s("seo, Doo-ok", 20, "Computer"); s.showdata(); return 0; 12
상속클래스의객체생성및소멸 (cont d) 상속클래스의객체소멸과정 1. Derived 클래스의소멸자실행 2. Base 클래스의소멸자실행 BaseClass BaseClass(); ~BaseClass(); DerivedClass DerivedClass(); ~DerivedClass(); 13
상속클래스의객체생성및소멸 (cont d) 프로그램예제 : 상속클래스의객체소멸과정 #include <iostream> using std::cin; using std::cout; using std::endl; class BaseClass BaseClass() cout << "Base Class!!!" << endl; ~BaseClass() cout << "~Base Class!!!" << endl; class DerivedClass : public BaseClass DerivedClass() cout << "DerivedClass Class!!!" << endl; ~DerivedClass() cout << "~DerivedClass Class!!!" << endl; int main() DerivedClass c; return 0; 14
상속의조건 IS-A 관계에의한상속 ~ 은 ~ 이다 가성립하는관계 A student is a person 학생은 ( 일종의 ) 사람이다. Person 불성립 성립 Student class Student : public Person 15
상속의조건 (cont d) IS-A 관계에의한상속 (cont d) 잘못된상속구조 Student 성립 불성립 Person class Person : public Student 16
상속의조건 (cont d) HAS-A(HAVE-A) 관계에의한상속 : 포함관계 하나의클래스가다른클래스의객체를멤버로가지고있을경우 Cudgel HAS-A 관계 The police have a Cudgel. 경찰은몽둥이를소유한다. Police 17
상속의조건 (cont d) HAS-A(HAVE-A) 관계에의한상속 (cont d) 클래스객체멤버 class Cudgel void Swing(void) cout << "Swing a cudgel1!!" << endl; class Police Cudgel c; // 객체멤버 void Useweapon(void) c.swing(); 18
상속의조건 (cont d) 프로그램예제 : HAS-A 관계에의한상속 #include <iostream> using std::cin; using std::cout; using std::endl; class Cudgel void Swing(void) cout << "Swing a cudgel!!!" << endl; class Police Cudgel c; void Useweapon(void) c.swing(); int main() Police p; p.useweapon(); return 0; void Swing(); Cudgel c; Cudgel Student void Useweapon(); 19
상속과다형성 상속의이해 상속과다형성 상속된객체와포인터, 참조 함수재정의 가상함수 다중상속 20
객체포인터 상속된객체와포인터, 참조 객체의주소값을저장할수있는포인터 Person Person Person *p = new Person; *p = new Student; *p = new PartTimeStudent; Person 클래스의객체포인터 (Person *) 는어떤대상체를가리키든지, Person 클래스내에선언된멤버와 Person 클래스가상속한클래스의멤버에만접근이가능하다. 21
상속된객체와포인터, 참조 참조 (cont d) 프로그램예제 : 상속된객체와포인터 (1/2) #include <iostream> using std::cin; using std::cout; using std::endl; class Person void Sleep(void) cout << "Sleep!!!" << endl; class Student : public Person void Study(void) cout << "Study!!!" << endl; class PartTimeStudent : public Student void Work(void) cout << "Work!!!" << endl; Person void Sleep(); Student void Study(); PartTimeStudent void Work(); 22
상속된객체와포인터, 참조 참조 (cont d) 프로그램예제 : 상속된객체와포인터 (2/2) int main() Person Person Person *p1 = new Person; *p2 = new Student; *p3 = new PartTimeStudent; p1->sleep(); p2->sleep(); p3->sleep(); return 0; Person *p3 = new PartTimeStudent; p3->sleep(); // p3->study(); // error // p3->work(); // error 23
상속된객체와포인터, 참조 객체참조 (Reference) 객체를참조할수있는레퍼런스 참조 (cont d) Person p; Person &r = p; Person 클래스의레퍼런스 (Person &) 는어떤대상체를가리키든지, Person 클래스내에선언된멤버와 Person 클래스가상속한클래스의멤버에만접근이가능하다. 24
상속된객체와포인터, 참조 참조 (cont d) 프로그램예제 : 상속된객체와참조 (1/2) #include <iostream> using std::cin; using std::cout; using std::endl; class Person void Sleep(void) cout << "Sleep!!!" << endl; class Student : public Person void Study(void) cout << "Study!!!" << endl; class PartTimeStudent : public Student void Work(void) cout << "Work!!!" << endl; Person void Sleep(); Student void Study(); PartTimeStudent void Work(); 25
상속된객체와포인터, 참조 참조 (cont d) 프로그램예제 : 상속된객체와레퍼런스 (2/2) int main() PartTimeStudent p; PartTimeStudent p; Person &r1 = p; Person &r1 = p; Student &r2 = p; r1.sleep(); PartTimeStudent &r3 = p; // r2.study(); // error r1.sleep(); r2.sleep(); r3.sleep(); // r3.work(); // error return 0; 26
함수재정의 (Overriding) 함수재정의 부모클래스에서선언된형태의함수를자식클래스에서다시 선언하는기능을제공 이전에정의된함수를숨기는 (hide) 특성을지닌다. class BaseClass BaseClass void Show(void) void Show(); cout << "BaseClass!!!" << endl; DerivedClass class DerivedClass : public BaseClass void Show(); void Show(void) cout << "DerivedClass!!!" << endl; 27
함수재정의 (cont d) 프로그램예제 : 함수재정의 -- overriding (1/2) #include <iostream> using std::cin; using std::cout; using std::endl; class BaseClass void Show(void) cout << "BaseClass!!!" << endl; class DerivedClass : public BaseClass void Show(void) cout << "DerivedClass!!!" << endl; int main(void) DerivedClass d; d.show(); return 0; 28
함수재정의 (cont d) Static Binding & Dynamic Binding 정적결합 (Static Binding) 호출할함수를컴파일하는과정 ( 컴파일 - 타임 ) 에서결정된다. 객체의이름과직접멤버접근연산자 () (.) 를사용하여 virtual 함수를호출 동적결합 (Dynamic Binding) 지연결합 (Late Binding) 호출할함수를실행하는과정 ( 런 - 타임 ) 에서결정된다. 포인터와참조를통해서만발생한다. 29
함수재정의 (cont d) 프로그램예제 : 함수재정의 -- overriding (1/2) #include <iostream> using std::cin; using std::cout; using std::endl; class BaseClass void Show(void) cout << "BaseClass!!!" << endl; class DerivedClass : public BaseClass void Show(void) cout << "DerivedClass!!!" << endl; 30
함수재정의 (cont d) 프로그램예제 : 함수재정의 -- overriding (2/2) int main(void) id) BaseClass B; B.Show(); DerivedClass D; D.Show(); DerivedClass *pd = new DerivedClass; pd->show(); BaseClass pb->show(); *pb = pd; delete pd; return 0; 31
가상함수 (virtual function) 가상함수 함수재정의 (Overriding) 된함수를가상으로선언할수있다. class BaseClass 가상함수의특성은상속된다. // 가상함수 virtual void Show(void) cout << "BaseClass!!!" << endl; class DerivedClass : public BaseClass void Show(void) // virtual void Show(void) cout << "DerivedClass!!!" << endl; 32
가상함수 (cont d) 함수재정의 (Overriding) 된함수호출 범위지정연산자 (::) 를통해서오버라이딩된함수도호출가능 class BaseClass virtual void Show(void) cout << "BaseClass!!!" << endl; class DerivedClass : public BaseClass void Show(void) BaseClass::Show(); cout << "DerivedClass!!!" << endl; 33
가상함수 (cont d) 프로그램예제 : 오버라이딩된함수호출 (1/2) #include <iostream> using std::cin; using std::cout; using std::endl; class BaseClass virtual void Show(void) cout << "BaseClass!!!" << endl; class DerivedClass : public BaseClass void Show(void) BaseClass::Show(); cout << "DerivedClass!!!" << endl; 34
가상함수 (cont d) 프로그램예제 : 오버라이딩된함수호출 (2/2) int main() BaseClass *pb = new DerivedClass; cout << "--------------------" << endl; pb->show(); cout << "--------------------" << endl; pb->baseclass::show(); return 0; 35
가상함수 (cont d) 순수가상함수 (pure virtual function) 함수원형만가지고있는함수 ( 함수내용이정의되지않은함수 ) 추상클래스 (abstract class) 하나이상의멤버함수가순수가상함수인클래스 추상클래스는객체를생성하지못한다!!! class BaseClass // 순수가상함수 virtual void Show(void) = 0; // = 0 : 순수지정자 class DerivedClass : public BaseClass void Show(void) cout << "DerivedClass!!!" << endl; 36
가상함수 (cont d) 프로그램예제 : virtual 소멸자 (1/3) #include <iostream> #include <cstring> using std::cin; using std::cout; using std::endl; class BaseClass char *id; BaseClass(char *id) this->id = new char[strlen(id)+1]; strcpy(this->id, id); virtual ~BaseClass(void) delete []id; // virtual 소멸자 virtual void Show(void) cout << "id : " << id << endl; 37
가상함수 (cont d) 프로그램예제 : virtual 소멸자 (2/3) class DerivedClass : public BaseClass char *name; DerivedClass(char *id, char *name) : BaseClass(id) this->name = new char[strlen(name)+1]; strcpy(this->name, name); ~DerivedClass(void) delete []name; void Show(void) cout << "name : " << name << endl; 38
가상함수 (cont d) 프로그램예제 : virtual 소멸자 (3/3) int main(void) id) BaseClass *pb = new DerivedClass("2011001", " 서두옥 "); DerivedClass *pd = new DerivedClass("2011005", " 홍길동 "); pb->show(); pd->show(); delete pb; delete pd; return 0; 39
다중상속 상속의이해 상속과다형성 다중상속 virtual 상속 40
다중상속 다중상속 하나의 Derived 클래스가둘이상의 Base 클래스를상속 Base Class #1 Base Class #2 Derived Class 41
다중상속 상속 (cont d) 프로그램예제 : 다중상속 (1/2) #include <iostream> using std::cin; using std::cout; using std::endl; class SuperClass void Show_SuperClass(void) SuperClass(void) cout << "Super Class!!!" << endl; class BaseClass void Show_BaseClass(void) cout << "Base Class!!!" << endl; 42
다중상속 상속 (cont d) 프로그램예제 : 다중상속 (2/2) class DerivedClass : public SuperClass, public BaseClass void Show_DerivedClass(void) cout << "Derived Class!!!" << endl; Show_SuperClass(); Show_BaseClass(); int main() DerivedClass d; d.show_derivedclass(); return 0; 43
다중상속의모호성 다중상속 상속 (cont d) class SuperClass void Show() cout << "Super Class!!!" << endl; class BaseClass void Show() cout << "Base Class!!!" << endl; class DerivedClass : public SuperClass, public BaseClass void Show_DerivedClass() cout << "Derived Class!!!" << endl; Show(); // error Show(); // error // 해결방법 SuperClass::Show(); BaseClass::Show(); 44
다중상속 다중상속의모호성 (cont d) 상속 (cont d) Derived 클래스가간접적인경로를통해서 Super Class 를두번상속 Super Class Base Class #1 Base Class #2 Derived Class 45
다중상속 상속 (cont d) class SuperClass void Show() cout << "Super Class!!!" << endl; class BaseClass01 : public SuperClass void Show01() cout << "Base Class #1!!!" << endl; class BaseClass02 : public SuperClass void Show02() cout << "Base Class #2!!!" << endl; class DerivedClass : public BaseClass02, public BaseClass01 void Show_DerivedClass() cout << "Derived Class!!!" << endl; Show(); // error Show01(); Show02(); 다중상속의모호성!!! 46
virtual 상속 virtual 상속 class SuperClass void Show() cout << "Super Class!!!" << endl; class BaseClass01 : virtual public SuperClass void Show01() cout << "Base Class #1!!!" << endl; class BaseClass02 : virtual public SuperClass void Show02() cout << "Base Class #2!!!" << endl; 47
virtual 상속 (cont d) 프로그램예제 : virtual 상속 (1/3) #include <iostream> using std::cin; using std::cout; using std::endl; class SuperClass void Show(void) cout << "Super Class!!!" << endl; 48
virtual 상속 (cont d) 프로그램예제 : virtual 상속 (2/3) class BaseClass01 : virtual public SuperClass void Show01(void) cout << "Base Class #1!!!" << endl; class BaseClass02 : virtual public SuperClass void Show02(void) cout << "Base Class #2!!!" << endl; 49
virtual 상속 (cont d) 프로그램예제 : virtual 상속 (3/3) class DerivedClass : public BaseClass02, public BaseClass01 void Show_DerivedClass(void) cout << "Derived Class!!!" << endl; Show(); Show01(); Show02(); int main(void) DerivedClass d; d.show_derivedclass(); return 0; 50
참고문헌 [1] 윤성우, 열혈강의 C++ 프로그래밍, 프리렉, 2007. [2] 이현창, 뇌를자극하는 C++ 프로그래밍, 한빛미디어, 2008. [3] H.M. HM Deitel, P. J. Deitel, C++ HOW TO PROGRAM : 6th Edition, Prentice Hall, 2009. [4] Wikipedie, http://www.wikipedia.org/. 이강의자료는저작권법에따라보호받는저작물이므로무단전제와무단복제를금지하며, 내용의전부또는일부를이용하려면반드시저작권자의서면동의를받아야합니다. Copyright Clickseo.com. All rights reserved. 51