简体   繁体   中英

Difference between two ways of declaring an object on the stack

What's the difference between the following two declarations, assuming I have not specified a copy constructor and operator= in class Beatle ?

Beatle john(paul);

and

Beatle john = paul;

Edit:

In objects assignment, the operator = implicitly calls the copy constructor unless told otherwise?

They're different grammatical constructions. The first one is direct initialization , the second is copy initialization . They behave virtually identically, only that the second requires a non- explicit constructor.*

Neither has anything to do with the assignment operator, as both lines are initializations .

To wit: const int i = 4; is fine, but const int i; i = 4; const int i; i = 4; is not.

*) More accurately: The second version does not work if the relevant constructor is declared explicit . More generally, thus, direct-initialization affords you one "free" conversion:

struct Foo { Foo(std::string) {} };

Foo x("abc");  // OK: char(&)[4] -> const char * -> std::string -> Foo
Foo y = "abd"; // Error: no one-step implicit conversion of UDTs

To address your edit: To understand the assignment operator, just break it up into parts. Suppose Foo has the obvious operator=(const Foo & rhs) . We can say x = y; , which just calls the operator directly with rhs being y . Now consider this:

x = "abc";              // error, no one-step implicit conversion
x = std::string("abc"); // fine, uses Foo(std::string), then copy
x = Foo("abc");         // fine, implicit char(&)[4] -> const char* -> std::string, then as above

First is Direct Initialization & second is Copy Initialization.

Direct initialization means the object is initialized using a single (possibly conversion) constructor, and is equivalent to the form T t(u); :

U u;
T t1(u); // calls T::T( U& ) or similar

Copy initialization means the object is initialized using the copy constructor, after first calling a user-defined conversion if necessary, and is equivalent to the form T t = u; :

T t2 = t1;  // same type: calls T::T( T& ) or similar
T t3 = u;   // different type: calls T::T( T(u) )
            //  or T::T( u.operator T() ) or similar

Copy Initialization does not work if the constructor is declared explicit .

References:
This entry in Herb Sutter's GOTW should be a good read.


To answer your edited Question:
= has a different meaning in depending on how it is used.

If = is used in an expression in which the object is being created and initialized at the same time, then = is not treated as Assignment Operator but as Copy Initialization.

If = is being used to assign one object to another, after the object has been created then it results in call to Assignment Operator.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM