복사 생성자를 공부하던 중

이러한 코드에서 복사 생성자가 호출되는가? 에 대한 자문을 해보았을 때

MyClass a = 2; // MyClass(int) 으로 오버로딩된 생성자가 있으니 type casting가능
MyClass a = MyClass(2); //임시객체 생성으로 오버로딩 생성자 호출
MyClass a(MyClass(2)); //복사생성자 호출하여 복사

이러한 과정으로 예측을 하여, 나는 무조건 호출되겠지 라고 생각을 했었다.

2가 임시객체가 되는 이유 : https://ddidding.tistory.com/98

 

근데 실행을 해보면 

복사 생성자가 실행이 되지 않는다.

어셈블리로 확인을 해보아도 오버로딩 생성자 하나만 호출될 뿐이였다.

호출되는 생성자는 복사 생성자가 아닌 오버로딩 생성자

즉, 이러한 과정이 된다는건데

MyClass a = 2 -----> MyClass a(2)

 

아무리 찾아도 저렇게 변환된다는 문법을 찾을 수 가 없었다 ㅅㅂ..😢

 

그러다가 이게 정말 생략되었다는 느낌이 강하게 들어서 컴파일러의 최적화 문제인가 싶어서 검색중에

Copy elision이라는 컴파일 옵션을 알게되었다.

 


Copy elision


Copy elision : 객체의 불필요한 복사를 제거할 수 있는 컴파일러 최적화 기술

std 12/31

이러한 Copy elision는 다음과 같은 상황에서 허용된다.

std 12/31

이 중에 지금 31.3을 해석 해보면 딱 지금과 같은 상황이다.

참조에 바인딩되지 않은 임시 클래스 객체가
동일한 유형의 클래스 객체로 복사/이동될 때(cv-unqualification 일때),
임시 객체를 대상에 직접 생성하여 복사/이동 작업을 생략할 수 있습니다.

MyClass a = 2; 에서

참조에 바인딩 되지 않은 임시 클래스 객체

= 2가 type casting으로 MyClass(2)가 되면서 임시객체가 됨

동일한 유형의 클래스 객체로 복사될 때(const, volatile가 아닐때)

= a와 임시객체는 같은 MyClass 타입으로, 동일한 유형의 클래스 객체로 복사 된다고 볼 수 있다.

 

코드로 보자면 이러하다.

copy elision이 된 경우는 복사가 생략되어 임시 객체가 생성이 되지 않는다.

 

그런데 "임시 객체를 대상에 직접 구성" 이라는건 무슨 뜻일까?

이게 나에겐 두가지 의미로 다가와서 굉장히 헷갈렸었다.

더보기

 

1. 임시 객체를 생성하고 그걸 대상에 직접 구성한다.

MyClass a = MyClass(2)
//copy elision
MyClass a(임시객체)

2. 임시 객체를 생성 하지 않고 대상에 직접 생성자를 호출하여 최적화

MyClass a = MyClass(2)
//copy elision
MyClass a(2)

굉장히 여러군데 찾아보면서 생각했다.

근데 애시당초 1번은

지금 복사 생성자가 호출이 안되서 찾아보고있는데 MyClass a(임시객체)에서는 복사 생성자 호출이 돼서

사실 생각할 것도 없었다. 나는 버드..?

게다가 답이 2번이라는 사실은 어셈블리에 이미 답이 있었다..ㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅅㅂ...

 

약간 임시객체에 꽂혀서 "임시 객체를 대상에 직접 구성" 을 보니까

"임시객체가 생성된다고ㅅㅂ?!!?!" 라고 바로 생각도 안하고 머리속에서 정의내려버리니까

답을 찾는데 굉장히 시간이 더 걸렸다.

 

다음부터는 좀 더 자세히 뜻을 파악하고 근본 원인에 대해 신경은 쓰고 있어야겠다.

한글을 이해 못해서 일어난 문제라 씁슬하다...

 

복사/이동 작업을 생략한거지

임시객체의 생성을 생략한건 아니지않나?

라는 생각도 들었었는데

복사가 생략되면서 임시객체의 생성도 생략되었다.

 

자 여기서 복사 대입 연산자는 copy elision이 적용되는가? 한다면

참조에 바인딩되지 않은 임시 클래스 객체

라 명시되어 있기 때문에 더 생각할 필요는 없겠다.

 


 

결론

copy elision라는 최적화 기능으로 인해 복사 생성자가 생략되는 경우가 있었다.

그 방법은 임시객체가 대상으로 바로 생성되게하여 복사를 생략하는 방법이였다.

 

그리고 copy elision에 대해 함수부분으로 RVO, NRVO같은 개념이 있는데 이건 일단 나중에 다뤄야겠다.

 

 

https://shaharmike.com/cpp/rvo/

 

Return Value Optimization | Shahar Mike's Web Spot

Return Value Optimization (1096 words) Fri, Aug 18, 2017 Return Value Optimization (RVO), Named RVO (NRVO) and Copy-Elision are in C++ since C++98. In this post I will explain what these concepts mean and how they help improve runtime performance. I will u

shaharmike.com

 

https://stackoverflow.com/questions/6383639/conditions-for-copy-elision

 

Conditions for copy elision?

I wanted to verify the if the following optimizations work as expected: RVO Named RVO Copy elision when passing an argument by value So I wrote this little program: #include <algorithm> #i...

stackoverflow.com

https://kldp.org/node/158078

 

c++ string 클래스의 원리에 있어 궁금한 것이 있습니다. | KLDP

글쓴이: 익명 사용자 / 작성시간: 토, 2017/08/12 - 10:05오후 연습으로 string 클래스를 만들어보고 있는데요(아주 기본적인 것들로만요..하하하) 일반적으로 string 클래스를 이용할 때 string str1 = "Happy c

kldp.org

https://kldp.org/node/157183

 

c++ 생성자에 반환형 없나요? | KLDP

글쓴이: 익명 사용자 / 작성시간: 수, 2017/03/15 - 6:14오후 제가 생각했을때 컴파일 타임에 컴파일러가 추가시킬거 같은데 그래야 Class c = Class(); 이런 생성자 반환값 대입 문장이 유효하지 않나요?

kldp.org

https://en.wikipedia.org/wiki/Copy_elision

 

Copy elision - Wikipedia

From Wikipedia, the free encyclopedia Jump to navigation Jump to search Compiler optimization in the C++ programming language eliminating unnecessary copying of objects In C++ computer programming, copy elision refers to a compiler optimization technique t

en.wikipedia.org

https://stackoverflow.com/questions/1758142/why-copy-constructor-is-not-called-in-this-case#comment1649230_1758617

 

Why copy constructor is not called in this case?

Here is the little code snippet: class A { public: A(int value) : value_(value) { cout <<"Regular constructor" <<endl; } A(const A& other) : value_(other.

stackoverflow.com

https://ko.cppreference.com/w/cpp/language/copy_elision

 

copy elision - cppreference.com

복사 및 이동 생성자를 무복사 값에 의한 전달(zero-copy pass-by-value)로 최적화 하는 것을 말합니다. 아래와 같은 상황일 때 컴파일러는 객체의 복사 및 이동 생성자를 생략합니다. 심지어 복사/이동

ko.cppreference.com

https://stackoverflow.com/questions/12953127/what-are-copy-elision-and-return-value-optimization/12953145#12953145

 

What are copy elision and return value optimization?

What is copy elision? What is (named) return value optimization? What do they imply? In what situations can they occur? What are limitations? If you were referenced to this question, you're proba...

stackoverflow.com

+ Recent posts