KoreanFoodie's Study

C++ 기초 개념 4-6 : explicit과 mutable 키워드 본문

Tutorials/C++ : Beginner

C++ 기초 개념 4-6 : explicit과 mutable 키워드

GoldGiver 2021. 12. 22. 11:43

모두의 코드를 참고하여 핵심 내용을 간추리고 있습니다. 자세한 내용은 모두의 코드의 씹어먹는 C++ 강좌를 참고해 주세요!

explicit 키워드

explicit 키워드는, 간단히 말해 암시적 형 변환을 허용하지 않을 때 붙여주는 키워드이다.

예를 들어, 이전에 만들었던 MyString 클래스에 다음과 같은 생성자와 함수를 추가한다고 가정해 보자.

MyString::MyString(int capacity) {
    string_length = 0;
    string_content = new char[capacity];
    memory_capacity = capacity;
}

void MyString::DoSomething(MyString s) {};

 

만약, explicit이 없다면, 다음과 같은 호출은 정상적으로 작동할 것이다.

MyString s1 = MyString(5);
MyString s2 = 5;

s2 = 5는 언뜻 보면 타입이 달라 불가능할 것 같지만, 컴파일러는 s1의 호출처럼 5를 암시적 형변환(implicit conversion)을 통해 int 타입을 받는 생성자를 호출하는 것이다.

 

하지만 만약 MyString::MyString(int capacity) 생성자에 다음과 같이 explicit이 붙어 있다면,

explicit MyString(int capacity);

// ...

MyString s3 = 5; // Error! no known conversion from 'int' to 'MyString'

타입에 맞게 Conversion을 할 수가 없어 에러가 발생하게 된다.

 

 

mutable 키워드

const 함수 내부에서는 멤버 변수들의 값을 바꾸는 것이 불가능하다. 하지만, 만약에 멤버 변수를 mutable로 선언하였다면 const 함수에서도 이들 값을 바꿀 수 있다.

아래 예제를 보자.

class A {
    int data_;
    mutable int data_m_;
    
    public:
    	A(int data) : data_(data) {}
        void change(int x) const {
            data_ = x; // Impossible!
            data_m_ = x; // Possible!
        }
}

const로 정의된 change 함수에서는 mutable로 정의된 data_m_의 값만 변경할 수 있다.

 

mutable이 필요한 이유?

예를 들어, 데이터 베이스에서 유저 정보를 얻어오는 함수가 있다고 가정해 보자. 그런데 DB에서 값을 요청하는 작업은 시간이 많이 걸리므로, 자주 조회하는 정보를 캐시 메모리에 저장하기도 한다. 예시 코드를 보자.

class Server {

    mutable Cache cache;
    
    User GetUserInfo(const int user_id) const {
    
        // 1. 캐쉬에서 user_id 검색
        Data user_data = cache.find(user_id);
        
        // 2. 캐시에 데이터가 없다면 데이터베이스에 요청
        if (!user_data) {
            user_data = Database.find(user_id);
        }
        
        // 그 후, 캐시에 유저 정보 추가
        // const 함수이므로, cache가 mutable이어야 추가 가능
        cache.update(user_id, user_data);
        
        // 3. 유저 정보 리턴
        return User(user_data);
    }

}

위 경우에서, 일반적으로 GetUserInfo는 const 함수이어야 한다. 다만 캐시에 유저 정보를 갱신하는 과정에서 캐시의 데이터를 건드리므로, cache를 mutable로 선언하면 효율적으로 코드를 동작하도록 만들 수 있다!

Comments