pkturner@cup.portal.com (Prescott K Turner) (05/23/90)
rfg@paris.ics.uci.edu (Ronald Guilmette) writes: > // I have just started to look at the code generated for simple statements of > // the general form: base = derived; > // > // It seems that the legality of such statements relies on the use of > // base::operator=(const base&) operators (which are implicitly generated > // by the compiler when not explicitly declared) and upon automatic implicit > // (multi-stage?) conversions of values of type `derived' to values of type > // `base&'. More precisely, an lvalue of type derived is converted directly to a reference to base. > // It seems to me that uses of these (sometimes implicitly generated) assignm ent > // operators should mean that statements of the general form shown above shou > // never involve the creation of temporaries or calls to constructors or > // destructors. The rule for initializing references changed as of cfront 2.0. It applies to parameters such as the "const base &" in the implicitly-generated assignment operator for base. For certain types of actual arguments, a temporary is created (implying calls to constructors and destructors). > base_object = derived_object; In this assignment statement, the derived object is not const. I don't think the annotated reference manual is clear on this, but it seems sufficient grounds for cfront to create a temporary. -- Prescott K. Turner, Jr. Language Processors, Inc. 959 Concord St., Framingham, MA 01701 USA (508) 626-0006 x232 UUCP: ...sun!cup.portal.com!pkturner Internet: pkturner@cup.portal.com
rfg@ics.uci.edu (Ronald Guilmette) (05/29/90)
In article <30152@cup.portal.com> pkturner@cup.portal.com (Prescott K Turner) writes: >rfg@paris.ics.uci.edu (Ronald Guilmette) writes: >> // I have just started to look at the code generated for simple statements of >> // the general form: base = derived; >> // >> // It seems that the legality of such statements relies on the use of >> // base::operator=(const base&) operators (which are implicitly generated >> // by the compiler when not explicitly declared) and upon automatic implicit >> // (multi-stage?) conversions of values of type `derived' to values of type >> // `base&'. >More precisely, an lvalue of type derived is converted directly to a reference >to base. > >> // It seems to me that uses of these (sometimes implicitly generated) assignm >ent >> // operators should mean that statements of the general form shown above shou > >> // never involve the creation of temporaries or calls to constructors or >> // destructors. >The rule for initializing references changed as of cfront 2.0. It applies >to parameters such as the "const base &" in the implicitly-generated >assignment operator for base. For certain types of actual arguments, >a temporary is created (implying calls to constructors and destructors). Prescott, Correct me if I am wrong, but I believe that the current (2.0) rules say that if an object (possibly a formal parameter object) of some reference-to-const type is initialized with an lvalue of the given type (or with a const value of the given type or with a const or non-const value of a type derived from the given type) no temporary is created. If my assertion is correct, then (as my original posting said) no temporaries are needed (or allowed) for any of my cases of "base = derived;". >> base_object = derived_object; >In this assignment statement, the derived object is not const. I don't think >the annotated reference manual is clear on this, but it seems sufficient >grounds for cfront to create a temporary. I disagree completely. I believe that the above statement may (and should) be interpreted as being equivalent to the following (more explicit) form: base_object = (const base&) (base&) (derived&) derived_object; Here there is an implicit conversion of the value of type "derived" to a value of type "derived&". This implicit conversion is supplied by the compiler and should *not* involve the creation of temporaries. Likewise, the compiler is allowed to implicitly convert a value of type "derived&" to a value of type "base&". In this case, a temporary of type "base&" may be needed to hold the result (converted) value (in order to deal with MI complications) but there should *definitely* NOT be any temporaries of type "base" or of type "derived" introduced. Finally, a value of type "base&" may be implicitly converted to a value of type "const base&" (again without any temporaries involved). If my analysis is incorrect, please tell me where I went wrong. // Ron Guilmette (rfg@ics.uci.edu) // C++ Entomologist // Motto: If it sticks, force it. If it breaks, it needed replacing anyway.