전체 코드

🚀 1. 개요

C++11에서 도입된 = delete 키워드는 특정 함수(연산자 포함)의 사용을 금지하고,
컴파일 단계에서 에러를 발생시켜 불필요한 호출을 차단하는 기능을 제공합니다.

= delete가 필요한 이유
이전 방식과 비교 (private 접근 제어와 friend 문제점)
실제 사용 예제 및 코드 분석

이 문서에서는 = delete의 필요성과 사용법을 예제 코드와 함께 상세히 분석하겠습니다.


📂 2. 코드 분석

🎯 기본 클래스 Knight

class Knight
{
public:
    void operator=(const Knight& k) = delete;

복사 대입 연산자 삭제

  • operator= 연산자를 삭제된 함수 (= delete) 로 선언하여 복사 대입 연산을 금지.
  • = delete는 해당 함수 호출을 컴파일러 수준에서 차단하므로,
    실수로 복사 대입을 시도하면 컴파일 에러 발생.
  • C++11 이전 방식(private 접근 제어)보다 명확하고 안전한 방법.

🎯 C++11 이전의 기존 방식

// 예전 문법
private:
    // 정의되지 않은 비공개(private) 함수
    void operator=(const Knight& k);

C++11 이전에는 private으로 복사 대입을 차단

  • operator=private으로 선언하면 외부에서 직접 호출 불가능.
  • 하지만 friend를 통해 접근할 수 있어 완벽한 방어가 아님.
  • 구현부가 없으면 링크 단계에서 에러 발생(= 조기에 문제 발견이 어려움).

🎯 기존 방식의 문제점 (friend 접근)

class Admin
{
public:
    void CopyKnight(const Knight& k)
    {
        Knight k1;
        // k1 = k; // friend 키워드를 사용하면 private 복사도 가능
        // delete 사용을 권장

friend를 사용하면 private 복사 대입도 호출 가능
C++11 이전 방식의 취약점

  • private으로 선언했지만, friend 클래스를 통해 접근하면 차단이 무력화됨.
  • = delete를 사용하면 이런 문제를 컴파일러 수준에서 완전히 차단 가능.

        // k1 = k; // 에러 발생 (컴파일 단계에서 차단됨)
    }
};

k1 = k;operator== delete이므로 컴파일 에러 발생

  • C++11 이전에는 링크 에러 발생했지만,
    = delete를 사용하면 컴파일러가 조기에 문제를 발견.

🎯 main() 함수 분석

🔹 복사 대입 연산 금지 확인

int main()
{
    Knight k1;
    Knight k2;
    // k1 = k2; // 안됨 (컴파일 에러 발생)

복사 대입 연산 (k1 = k2;) 금지됨

  • operator=가 삭제되었으므로 컴파일러가 즉시 에러 발생.
  • 객체 복사를 방지하여 불필요한 메모리 복사 비용을 절약.

🔹 Admin 클래스를 통한 복사 시도

    Admin admin;
    // admin.CopyKnight(k1); // 컴파일 에러 발생

Admin::CopyKnight() 내부에서 operator=를 호출하므로 에러 발생

  • 복사 대입이 필요하면 명시적으로 구현해야 함.
  • = delete를 사용하면 잘못된 코드가 실행되지 않도록 차단 가능.

📌 3. = delete vs 기존 방식 비교

기능기존 방식 (private)= delete
복사 대입 차단private으로 제한하지만 완벽하지 않음완전히 차단 (컴파일 에러)
friend 문제friend 클래스를 사용하면 우회 가능friend 사용 여부와 관계없이 차단
링크 에러조기에 발견 어려움 (링크 단계에서 에러)컴파일 단계에서 즉시 발견
사용법private에 선언하고 구현부 제거= delete 한 줄이면 끝!
가독성명확하지 않음= delete로 의도가 명확

C++11 이후에는 = delete 사용을 권장!
컴파일 단계에서 즉시 차단하여 조기에 오류 발견 가능!


📌 4. = delete의 활용 예제

🔹 복사 생성자 삭제 (Singleton 패턴)

class Singleton
{
public:
    static Singleton& GetInstance()
    {
        static Singleton instance;
        return instance;
    }

    Singleton(const Singleton&) = delete;
    void operator=(const Singleton&) = delete;

private:
    Singleton() {}  // 기본 생성자 `private`
};

Singleton 패턴에서 복사/대입을 금지하여 객체 중복 생성 방지
= delete를 사용하면 컴파일 단계에서 실수로 복사하는 문제를 완벽히 차단


🔹 기본 생성자 삭제

class NonInstantiable
{
private:
    NonInstantiable() = delete; // 기본 생성자를 삭제하여 객체 생성 차단
};

객체 생성이 필요 없는 클래스를 만들 때 활용
예제: static 함수만 존재하는 유틸리티 클래스


🔹 특정 타입 변환 금지

class Example
{
public:
    Example(int x) {}

    Example(double) = delete; // `double`을 `int`로 변환하는 것을 금지
};

int main()
{
    Example e1(10);   // OK
    // Example e2(3.14); // 컴파일 에러 발생
}

특정 타입 변환을 명확히 차단
잘못된 타입 사용을 방지하여 코드 안정성을 높임


profile
李家네_공부방

0개의 댓글