[C++] 클래스 상속


Study/C , C++ , MFC  2020. 3. 19. 02:11

안녕하세요. 명월입니다.


이 글은 C++에서 클래스 상속에 대한 글입니다.


C++도 클래스가 있기 때문에 당연히 상속 기능이 있습니다.

그러나 Java와 C#과는 다르게 C++은 다중 상속이 가능합니다. 이유는 C++은 interface가 존재하지 않습니다. 해더(.h)나 구조체를 전처리문으로 설정한 interface는 엄밀히 말해 인터페이스가 아닙니다.

Java나 C#은 interface를 통해서 한 클래스가 여러 interface를 상속 받을 수 있습니다. 그러나 interface가 아닌 abstract 클래스나 일반 클래스의 경우는 두개가 이상의 클래스를 상속 받을 수 없습니다.

그러나 C++은 interface가 없기 때문에 여러 클래스를 상속 받을 수 있는 방법이 필요합니다. 그래서 다중 상속이 있습니다.

#pragma once
#include <stdio.h>
#include <iostream>
using namespace std;
// AClass 클래스
class AClass
{
public:
  // atest 함수
  void atest()
  {
    // 콘솔 출력
    cout << " AClass atest function " << endl;
  }
  // print1 함수
  void print1()
  {
    // 콘솔 출력
    cout << " AClass print " << endl;
  }
};
#pragma once
#include <stdio.h>
#include <iostream>
using namespace std;
// BClass 클래스
class BClass
{
public:
  // btest 함수
  void btest()
  {
    // 콘솔 출력
    cout << " BClass btest function " << endl;
  }
  // print2 함수
  void print2()
  {
    // 콘솔 출력
    cout << " BClass print " << endl;
  }
};
#include <stdio.h>
#include <iostream>
// 클래스 해더 선언
#include "AClass.h"
#include "BClass.h"
using namespace std;
// C클래스, AClass와 BClass를 상속받는다.
class CClass : public AClass, public BClass
{
public:
  // atest 함수 재정의
  virtual void atest() 
  {
    // 콘솔 출력
    cout << " CClass atest function " << endl;
    // 부모 클래스의 함수 호출
    AClass::atest();
  }
  // btest 함수 재정의
  virtual void btest()
  {
    // 콘솔 출력
    cout << " CClass btest function " << endl;
    // 부모 클래스의 함수 호출
    BClass::btest();
  }
};
// 실행 함수
int main()
{
  // 클래스 선언
  CClass obj;
  // atest 함수 호출
  obj.atest();
  // btest 함수 호출
  obj.btest();
  // print1 함수 호출
  obj.print1();
  // print2 함수 호출
  obj.print2();

  return 0;
}

위처럼 두 개의 클래스를 상속받고 Class에서 두 클래스의 함수도 사용하고 재정의도 가능합니다.

여기에서 왜 Java와 C#이 다중 상속이 없어지는 이유가 만약 AClass와 BClass에서 같은 함수가 있을 경우, 호출을 하게 되면 어떤 함수를 호출하게 될까요?

이게 다중 상속의 모호점이 생깁니다.

#pragma once
#include <stdio.h>
#include <iostream>
using namespace std;
// AClass 클래스
class AClass
{
public:
  // print 함수
  void print()
  {
    // 콘솔 출력
    cout << " AClass print " << endl;
  }
};
#pragma once
#include <stdio.h>
#include <iostream>
using namespace std;
// BClass 클래스
class BClass
{
public:
  // print 함수
  void print()
  {
    // 콘솔 출력
    cout << " BClass print " << endl;
  }
};
#include <stdio.h>
#include <iostream>
// 클래스 해더 선언
#include "AClass.h"
#include "BClass.h"
using namespace std;
// C클래스, AClass와 BClass를 상속받는다.
class CClass : public AClass, public BClass
{
};

int main()
{
  // 클래스 선언
  CClass obj;
  // print 함수 호출
  obj.print();

  return 0;
}

다중 상속은 여러 클래스를 합쳐서 사용할 수 있는 이점은 분명히 있지만, 이런 모호점이 발생할 여지가 많습니다.

이걸 해결하기 위해서는 composite 패턴이나 adapter 패턴으로 돌려서 사용해야 하는 불편함이 있습니다.


여기까지 C++에서 클래스 상속에 대한 글이었습니다.


궁금한 점이나 잘못된 점이 있으면 댓글 부탁드립니다.