Menu
CoddyTech

소멸자 심층 탐구

Coddy C++ 여정의 객체 지향 프로그래밍 섹션에 포함된 레슨. 104개 중 24번째.

소멸자는 객체가 소멸될 때 자동으로 실행되는 특수 멤버 함수입니다. 주요 역할은 동적으로 할당된 메모리, 파일 핸들 또는 네트워크 연결과 같이 객체가 수명 동안 획득한 리소스를 해제하는 것입니다.

소멸자는 클래스와 같은 이름 앞에 물결표 ~를 붙인 이름을 가집니다. 매개변수를 받지 않으며 반환 형식도 없습니다:

class FileHandler {
    std::string filename;
    int* buffer;
public:
    FileHandler(std::string name, size_t size) 
        : filename(name), buffer(new int[size]) {
        std::cout << "Opening " << filename << "\n";
    }
    ~FileHandler() {
        delete[] buffer;
        std::cout << "Closing " << filename << "\n";
    }
};

소멸자는 다음과 같은 상황에서 자동으로 호출됩니다:

  • 스택 객체가 스코프를 벗어납니다
  • 힙에 할당된 객체에 delete가 호출됩니다
  • 임시 객체의 수명이 끝납니다
void example() {
    FileHandler f1("data.txt", 100);    // 생성자 호출됨
    FileHandler* f2 = new FileHandler("log.txt", 50);
    delete f2;                           // f2에 대한 소멸자 호출됨
}   // f1에 대한 소멸자 호출됨 (스코프를 벗어남)

생성자와 달리 클래스에는 소멸자가 하나만 있을 수 있습니다. 소멸자를 오버로드할 수는 없습니다.

직접 정의하지 않으면 컴파일러가 특별한 작업을 하지 않는 기본 소멸자를 생성합니다. 기본 소멸자는 각 멤버를 단순히 소멸시킵니다. 리소스를 관리하는 클래스에서는 메모리 누수를 방지하기 위해 직접 작성해야 합니다.

challenge icon

챌린지

쉬움

활성 사용자 세션을 추적하고 객체가 소멸될 때 범위를 벗어나거나 명시적으로 삭제되는 경우 소멸자가 리소스를 자동으로 정리하는 방식을 보여 주는 세션 관리자를 만들어 보겠습니다.

코드를 구성하기 위해 두 개의 파일을 만듭니다.

  • Session.h: 동적으로 할당된 데이터를 포함하는 활성 사용자 세션을 나타내는 Session 클래스를 정의합니다. 클래스에는 다음 항목이 있어야 합니다.
    • private 멤버: username(문자열), sessionId(int), 사용자 작업을 추적하는 activityLog라는 정수 배열에 대한 포인터, 그리고 배열 크기를 나타내는 logSize
    • 사용자 이름, 세션 ID, 로그 크기를 인수로 받는 생성자. 힙에 활동 로그 배열을 할당하고, 모든 요소를 0으로 초기화한 다음 "Session <sessionId> started for <username>"을 출력해야 합니다.
    • 할당된 메모리를 해제하고 "Session <sessionId> ended for <username>"을 출력하는 소멸자
    • 활동 코드를 다음 사용 가능한 위치에 저장하는 logActivity(int activityCode) 메서드(현재 위치를 내부적으로 추적). 로그가 이미 가득 찬 경우 호출을 무시하여 개수가 로그 크기를 초과하지 않도록 합니다.
    • 기록된 활동의 개수를 반환하는 getActivityCount() 메서드
    • 사용자 이름을 반환하는 getUsername() 메서드
  • main.cpp: 다양한 상황에서 소멸자가 동작하는 방식을 보여 줍니다. 입력에서 사용자 이름과 로그 크기를 읽습니다(각각 별도의 줄에 입력). 그런 다음 다음을 수행합니다.
    • 중괄호 { }를 사용하여 범위 블록을 만들고, 그 안에서 입력된 사용자 이름, 세션 ID 101, 입력된 로그 크기로 스택에 할당된 Session을 생성합니다. 코드 1과 2로 두 개의 활동을 기록한 다음 "Stack session activities: <count>"를 출력합니다. 블록이 끝나면 소멸자가 자동으로 실행되어야 합니다.
    • 블록 다음에 "Stack session destroyed"를 출력합니다.
    • 사용자 이름 "Guest", 세션 ID 202, 로그 크기 3으로 new를 사용하여 힙에 할당된 Session을 생성합니다. 코드 5로 활동 하나를 기록하고, "Heap session activities: <count>"를 출력한 다음 명시적으로 delete합니다.
    • 삭제한 다음 "Heap session destroyed"를 출력합니다.

이 챌린지는 소멸자가 호출되는 두 가지 주요 방식을 보여 줍니다. 스택 객체가 범위를 벗어날 때는 자동으로 호출되고, 힙 객체를 삭제할 때는 수동으로 호출됩니다. 두 경로 모두 동적으로 할당된 활동 로그를 적절히 해제하여 메모리 누수를 방지해야 합니다.

#include "Session.h"를 사용하여 헤더 파일을 main.cpp에 포함하세요.

직접 해보기

#include <iostream>
#include <string>
#include "Session.h"

using namespace std;

int main() {
    // 입력 읽기
    string username;
    int logSize;
    getline(cin, username);
    cin >> logSize;
    
    // TODO: 중괄호 { }로 스코프 블록 만들기
    // 블록 내부:
    //   - 입력 username, 세션 ID 101, 입력 log size로 스택에 할당된 Session 생성
    //   - 코드 1과 2로 두 개의 활동 로그
    //   - Print "Stack session activities: <count>"
    // 블록이 끝나면 소멸자가 자동으로 실행됩니다
    
    // TODO: After the block, print "Stack session destroyed"
    
    // TODO: new를 사용하여 힙에 할당된 Session 생성
    //   - Username: "Guest", session ID: 202, log size: 3
    //   - 코드 5로 활동 하나 로그
    //   - Print "Heap session activities: <count>"
    //   - 세션 삭제
    
    // TODO: After deletion, print "Heap session destroyed"
    
    return 0;
}
quiz icon실력 점검

이 레슨에는 짧은 퀴즈가 포함되어 있습니다. 레슨을 시작해 문제를 풀고 진행 상황을 기록하세요.

객체 지향 프로그래밍의 모든 레슨

직접 연습해 보세요: 온라인 C++ 컴파일러