열혈 C++의 8장. 상속과 다형성을 복습하고 가상함수에 대해 익혀오는 과제가 있었다.

두개의 소스코드를 볼 수 있는데, FunctionVirtualOverride.cpp와 EmployeeManager4.cpp였다.

우선 가상함수에 대해서 간단히 짚고 넘어가보자.

가상함수란 virtual 키워드를 일반적인 함수 앞에 붙임으로 그 함수가 오버라이딩을 할 수 있게 해준다.

오버라이딩을 통해 한가지 기능을 다른 여러가지 기능으로 쓸수 있는 '다형성'을 만들어낼 수 있다.

또한, 가상함수가 선언되고 나면, 이 함수를 오버라이딩 하는 다른 함수는 virtual을 붙이지 않아도 가상함수가 된다.

/* FunctionVirtualOverride.cpp 
   열혈 C++ 347-348p           */
 
#include <iostream>
using namespace std;

class First //First 클래스 생성
{
public:
	virtual void MyFunc() { cout<<"FirstFunc"<<endl; } // FirstFunc을 출력하는 가상함수 MyFunc
};

class Second: public First //First를 상속받는 Second 클래스 생성
{
public:
	virtual void MyFunc() { cout<<"SecondFunc"<<endl; } //굳이 추가하지 않아도 가상함수가 되나 가독성을 위해 선언을 넣기도 한다.
};

class Third: public Second //Second를 상속받는 Third 클래스 생성
{
public:
	virtual void MyFunc() { cout<<"ThirdFunc"<<endl; }
};

int main(void)
{
	Third * tptr = new Third(); //Third 객체를 생성해서 Third형 포인터 변수로 참조
    Second * sptr = tptr; //Second형 포인터 변수로 참조
    First * fptr = sptr; //First형 포인터 변수로 참조
    
    fptr->MyFunc();  //포인터변수로 MyFunc 함수 호출
    sptr->MyFunc();
    tptr->MyFunc();
    delete tptr;
    return 0;
}

가상함수를 호출할때, 포인터의 자료형을 기반으로 호출대상이 결정되지 않고, 포인터 변수가 실제로 가리키는 객체를 참조하여 호출의 대상을 결정한다.

/* EmployeeManager4.cpp
   열혈C++ 349-351p	 */

#include <iostream>
#include <cstring>
using namespace std;

class Employee
{
private:
	char name[100];
public:
	Employee(char * name)
    {
    	strcpy(this->name, name);
    }
	void ShowYourName() const
    {
    	cout<<"name: "<<name<<endl;
    }
    virtual int GetPay() const
    {
		return 0;
    }
    virtual void ShowSalaryInfo() const
    {}
};

class PermanentWorker : public Employee
{
private:
	int salary; //월 급여
public:
	PermanentWorker
};
class TemporaryWorker : public Employee
{

};
class SalesWorker : public PermanentWorker
{

};

class EmployeeHandler
{
private:
	Employee* emplist[50];
    {}
    void AddEmployee(Employee* emp)
    {
    	emplist[empNum++]=emp;
    }
    void ShowAllSalaryInfo() const
    {
    	for(int i=0; i<empNum; i++)
        	empList[i]->ShowSalaryInfo();
    }
    void ShowTotalSalary() const
    {
    	int sum=0;
        for(int i=0;i<empNum;i++)
        	sum+=empList[i]->GetPay();
        
        cout<<"salary sum: "<<sum<<endl;
    }
    ~EmployeeHandler()
    {
    	for(int i=0; i<empNum; i++)
        	delete empList[i];
    }
};

int main(void)
{
	//직원관리를 목적으로 설계된 컨트롤 클래스의 객체생성
    EmployeeHandler handler;
    
    //정규직 등록
    handler.AddEmployee(new PermanentWorker("KIM",1000));
	handler.AddEmployee(new PermanentWorker("LEE",1500));
    
    //임시직 등록
    TemporaryWorker* alba = new TemporaryWorker("Jung", 700);
    alba->AddWorkTime(5);
    handler.AddEmployee(alba);
    
    //영업직 등록
    SalesWorker* seller = new SalesWorker("Hong", 1000, 0.1);
    seller->AddSalesResult(7000);
	handler.AddEmployee(seller);
    
    //이번 달에 지불해야 할 급여의 정보
    handler.ShowAllSalaryInfo();
    
    //이번 달에 지불해야 할 급여의 총합
    handler.ShowTotalSalary();
    return 0;
]

'스터디 관련' 카테고리의 다른 글

CS스터디 02회차, ~06월 09일(목)  (0) 2022.06.09
CS스터디 01회차, ~06월 02일(목)  (0) 2022.06.02
2/3(수) 과제  (0) 2021.02.03
이번 스터디 과제,,  (0) 2020.12.31
소프트웨어 생명주기 6단계  (0) 2020.12.30

+ Recent posts