220915 C++ #6

김혜진·2022년 9월 15일
0

C++

목록 보기
6/12

C++ #6

복사 생성자

복사 생성자란

  • 객체 생성 시 초기화를 하되, 생성되는 객체를 다른 객체로 초기화 시에 호출한다.
String str1('A', 3);  // 일반 생성자 호출 1
String str2 = str1;  // 복사 생성자 호출 2
      혹은
String str2(str1);   // 복사 생성자 호출
  • 객체 간 대입의 문제점은 포인터 멤버변수인데, 값에 의한 복사 방식을 이용하면 객체 소멸 시 문제가 발생한다고 하였다.
  • 복사 생성자 또한 객체 간 복사이므로 이 문제를 처리해야 한다.
  • 복사 생성자의 특징은 다음과 같다.
    ① 함수명이 클래스와 동일하다.
    ② 반환형이 없다.

대입 연산자와의 차이점

  • 복사 생성자는 대입 연산자와의 객체 간 복사한다는 점에서 기능상 유사하지만 몇 가지 차이점이 있다.

1. 대입 연산자인 operator=() 멤버함수는 이미 생성된 객체에서만 호출되는 반면에 복사 생성자는 새로운 객체를 만들 때 호출된다. 따라서 operator=() 멤버함수는 원래 할당했던 메모리를 해제하고 새로 할당을 해야하지만, 복사 생성자는 객체가 처음 생성되는 시점이기 때문에 그럴 필요가 없다.

  1. 대입 연산자인 operator=() 멤버함수는 자기 자신의 객체를 대입하였는지 검사해야하지만, 복사 생성자는 자기 자신의 초기화가 불가능하기 때문에 그럴 필요가 없다.

  2. 대입 연산자인 operator=() 멤버함수는 다중 대입문을 지원해야하므로 *this를 반환해야 하지만, 복사 생성자는 생성자이기 때문에 반환값을 가질 수 없다.


상속

상속의 개념

  • 상속하면 자식이 부모로부터 재산을 물려받는 개념이다.
    "부모 A는 자식 B에게 100만원을 상속하였다.(물려주었다)"
    "부모 A는 자식 B에게 보조개를 상속하였다.(물려주었다)"

객체 지향에서의 상속성

  • 클래스란 사용자가 정의한 하나의 데이터형이다.
  • 완성된 하나의 데이터형인 클래스를 다른 클래스에 상속함으로써 기능을 제공할 수 있는데, 이것이 "객체지향에서의 상속성"이다.

회사 인사 시스템의 예

  • 회사 직원들은 크게 정규 직원과 계약 직원으로 나눌 수 있다.
  • 공통 사항: 이름, 주소와 같은 인적 사항
  • 차이점: 급여 지급 형태(정규 직원은 연봉제 형태, 계약 직원은 근무일과 근무 시간을 곱한 형태)
  • 상속의 개념은 당장 생각하지 말고, 회사 직원에 대한 정보 클래스를 위의 정보를 바탕으로 해서 Empoloyee라는 이름의 클래스를 작성해보자.
#include<iostream>

using namespace std;

class Employee
{
public:
	Employee();
	Employee(const char* pName, const char* pAddr);
	~Employee();
	void DisplayEmployee();
private:
	char* strName;
	char* strAddr;
};

Employee::Employee()
{
	strName = NULL;
	strAddr = NULL;
}

Employee::Employee(const char* pName, const char* pAddr)
{
	strName = new char[strlen(pName) + 1]; // strlen : 문자열 길이 리턴해주는 함수
	strAddr = new char[strlen(pAddr) + 1]; // \n값까지 포함해야해서 + 1
	strcpy_s(strName, strlen(pName) + 1, pName);
	strcpy_s(strAddr, strlen(pAddr) + 1, pAddr);
}

Employee::~Employee()
{
	delete strName;
	delete strAddr;
}

void Employee::DisplayEmployee()
{
	cout << "이름 : " << strName << endl;
	cout << "주소 : " << strAddr << endl;
}


void main()
{
	Employee emp("kim", "seoul");
	emp.DisplayEmployee();
}

부모 클래스와 자식 클래스의 개념

  • 앞서 작성한 클래스는 보편적인 회사 직원의 정보를 가진 클래스이다.
  • 정규 직원과 계약 직원에 대한 클래스를 나누지 않았다.
  • 정규 직원과 계약 직원으로 나누려면? 단순한 방법은 두 종류의 클래스를 따로 따로 제작하는 것이다.
  • 문제점 : 이름과 주소와 같은 공통 멤버가 중복 관리가 된다.
  • 해결 방법 : 상속성을 이용하여 공통으로 관리하고, 차이나는 급여 방식만 정규 직원과 계약 직원으로 나누어 관리한다.

클래스의 상속 구조

  • 클래스 간의 상속 구조 정의(정규 직원 클래스)
class 자식 클래스명 : 접근 지정자 부모 클래스명
{
	public:
    	반환형 함수명(매개변수);
    private:
    	데이터형 변수명;
}
class Regular : Employee
{
	public:
    	Regular();
        Regular(char* pName, char* pAddr, double dSalary);
        ~Regular();
        double payCheck() const;
    private:
    	double salary;
}

Regular 클래스는 Employee 클래스의 이름, 주소에 대한 멤버 변수들을 상속받았다.
Regular 클래스는 급여액 관련 멤버 변수 salary와 멤버함수 PayCheck() 함수만 별도 선언하였다.

  • 클래스 간의 상속 구조 계층도

이러한 부모 클래스와 자식 클래스 간의 관계를 '상속성'이라고 한다.

profile
알고 쓰자!

0개의 댓글