Path: utzoo!attcan!uunet!husc6!think!ames!decwrl!labrea!polya!shap From: shap@polya.Stanford.EDU (Jonathan S. Shapiro) Newsgroups: comp.lang.c++ Subject: Re: Two questions Message-ID: <5315@polya.Stanford.EDU> Date: 28 Nov 88 19:49:28 GMT References: <13683@oberon.USC.EDU> Reply-To: shap@polya.Stanford.EDU (Jonathan S. Shapiro) Distribution: na Organization: AT&T Bell Laboratories Lines: 87 In article <13683@oberon.USC.EDU> english@stromboli.usc.edu (Joe English) writes: > In the Book, section 8.5.1 (Static Members), p. 275, it states: >"No initializer can be specified for a static member, and __it cannot >be of a class with a constructor__." I'm not sure if I'm parsing this >sentence correctly: does it mean that a class with a constructor can >have no static members? Also, if no initializer can be specified, >where and how does a static member get initialized? I believe that what this means is that if I say: class Fred { static Member member; ... } where Member is also a class, then Member is not permitted to have a constructor. It is my vague recollection that this may have been relaxed to a lesser restriction: that Member can have a constructor that takes no arguments. Could someone confirm or deny this last bit? Bjarne? > Second question: if automatic temporary objects are created when >necessary and are destroyed at the first opportunity (like when a >function returns a class object), how does the compiler know when the >object is no longer needed? For example, is the following correct: > >[... much of example deleted ...] > >void diddle() > >{ > frobpvector v; > > v.append(frob(1)); // frob(1) returns a temporary > // ... > v.append(frob(2)); // frob(2) should be a *different* frob > > // ... do stuff with the frobs pointed to in v > >} I do not know quite what the scoping rules are for temporaries. I believe that GNU G++, for example, attempts to reuse the space and to peephole them out of existence when possible. In any case, I read "destroyed at the first opportunity" to mean "destroyed as soon as possible." My general reaction to this is that functions that accept an object reference are not entitled to assume that the object continues to exist after the function call. This means that the scope of the temporary above is free to be the temporal scope of the function call itself, and the compiler is free to destroy the object after the function call returns. If the fropvector wants to ensure that it retains a copy of the object, than in C++ it is necessary to make a copy. It also seems to me that if my understanding is correct, then applying foo(X&) to a temporary is for exactly this reason an unreasonable thing to do, and ought to be a compiler error. The compiler ought to apply foo(X), which presumably is smart enough to understand that the behavior must be copying. Until someone indicates what the correct behavior is, the safest bet is to modify your function to read: void diddle() { frobpvector v; Frob f1(1), f2(2); v.append(f1); v.append(f2); ... } As a side observation, this sort of detail is the kind of thing that compilers routinely get wrong or abuse in their optimization phases. It is therefore not a real good thing to rely on. Further, instantiating the temporaries explicitly makes it easier on the reader - it is now obvious that they are temporaries. Jonathan S. Shapiro AT&T Bell Laboratories