473,385 Members | 1,764 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,385 software developers and data experts.

Best way to return newly created object

Hi all,

Sometimes I have a function which creates an object and returns it.
Some are sets, other vectors but that's not very important. In these
cases I do something like this:

vector<int> * f() {
vector<int> * v = new vector<int>;
return v;
}

Would there be any other way without pointers?

Would this work:
vector<int>& f() {
vector<int> v;
return v;
}

???

Cheers,

Paulo Matos

Jul 23 '05 #1
29 2195
Geo


pmatos wrote:
Hi all,

Sometimes I have a function which creates an object and returns it.
Some are sets, other vectors but that's not very important. In these
cases I do something like this:

vector<int> * f() {
vector<int> * v = new vector<int>;
return v;
}

Would there be any other way without pointers?

Would this work:
vector<int>& f() {
vector<int> v;
return v;
}

???

Cheers,

Paulo Matos


No, that won't work, 'v' will be destroyed when 'f' returns, you will
have an invalid reference. You should consider returning a
std::auto_ptr, or some other smart pointer.

Jul 23 '05 #2
pmatos wrote:
Hi all,

Sometimes I have a function which creates an object and returns it.
Some are sets, other vectors but that's not very important. In these
cases I do something like this:

vector<int> * f() {
vector<int> * v = new vector<int>;
return v;
}

Would there be any other way without pointers?

Would this work:
vector<int>& f() {
vector<int> v;
return v;
}


No. Never return a reference to a local object.

What you could do is turn it around. Let the function take the vector as
parameter and fill it:

void f(vector<int>& vec)
{
//fill vec
}

Jul 23 '05 #3
"pmatos" <po**@sat.inesc-id.pt> schrieb:
vector<int> * f() {
vector<int> * v = new vector<int>;
return v;
}


I suggest not to return a newly created object. Nobody knows what to
do with the pointer. How it is created? Do we have to delete it? Is it
a pointer on the heap or just an address of an existing object?

Indeed if the function and its caller don't use the same heap
management it could result in a serious problem. This is the case if
you create an object in a DLL and return a pointer up to an
application. If both modules are linked with a static runtime library
the application cannot delete the pointer.

I suggest to create the object outside the function. You can use the
function to fill it.

void f (vector<int>& v)
{
// fill v ...
}

T.M.
Jul 23 '05 #4

"pmatos" <po**@sat.inesc-id.pt> wrote in message
news:11**********************@g47g2000cwa.googlegr oups.com...
Hi all,

Sometimes I have a function which creates an object and returns it.
Some are sets, other vectors but that's not very important. In these
cases I do something like this:

vector<int> * f() {
vector<int> * v = new vector<int>;
return v;
}

Would there be any other way without pointers?

Would this work:
vector<int>& f() {
vector<int> v;
return v;
}

???

Cheers,

Paulo Matos


vector<int> f()
{
return vector<int>;
}

regards,
ben
Jul 23 '05 #5
pmatos wrote:
Sometimes I have a function which creates an object and returns it.
Some are sets, other vectors but that's not very important. In these
cases I do something like this:

vector<int> * f() {
vector<int> * v = new vector<int>;
return v;
}
Thats usually a wrong way, because calling functions (which means the
programmer of the calling function) usually don't care about data not
created by themself.
Would this work:
vector<int>& f() {
vector<int> v;
return v;
}


Returning a ref to a local object is always wrong. Thinking about your
problem, the question arises:

In the calling function, you can either write:

vector<int> v;
or
vector<int> v = f();

I can't imagine a situation where someone would prefer the second solution.
So I assume you're trying to solve another problem. But without knowing
about it, nobody will be able to help you.

Mathias
Jul 23 '05 #6
"benben" <be******@hotmail.com> schrieb:
vector<int> f()
{
return vector<int>;
}


This will create a copy of the entire vector while the temporary
object will soon be forgotten unless the compiler supports a return
value optimization.

T.M.
Jul 23 '05 #7
Torsten Mueller wrote:
"benben" <be******@hotmail.com> schrieb:
vector<int> f()
{
return vector<int>;
}


This will create a copy of the entire vector while the temporary
object will soon be forgotten unless the compiler supports a return
value optimization.


Even _with_ RVO

vector<int> x = f()

will copy the vector twice.

Jul 23 '05 #8
"Panjandrum" <pa********@spambob.com> schrieb:
vector<int> f()
{
return vector<int>;
}


This will create a copy of the entire vector while the temporary
object will soon be forgotten unless the compiler supports a
return value optimization.


Even _with_ RVO

vector<int> x = f()

will copy the vector twice.


I had this in another news group some days ago. Look at the following
program:

#include <iostream>
using namespace std;

struct X
{
X() { cout << "X"; }
X( const X& ) { cout << "C"; }
};

X f()
{
return X();
}

X g()
{
X x;
return x;
}

#define TEST( code ) \
cout << #code << "\t: "; code; cout << endl

int main()
{
TEST( X x1( f() ); );
TEST( X x2( g() ); );
TEST( X const& x3 = f(); );
TEST( X const& x4 = g(); );
}

This little program compiles indeed different with several compilers.
I used the one I had on my machine. Look at this:

------------------------------------------------------------------------
MSVC 6

X x1( f() ); : X
X x2( g() ); : XC
X const& x3 = f(); : X
X const& x4 = g(); : XC
------------------------------------------------------------------------
MSVC 7.1

X x1( f() ); : X
X x2( g() ); : XC
X const& x3 = f(); : X
X const& x4 = g(); : XC
------------------------------------------------------------------------
gcc 3.2.3 (mingw)

X x1( f() ); : X
X x2( g() ); : X
X const& x3 = f(); : X
X const& x4 = g(); : X
------------------------------------------------------------------------
aCC (HP ANSI C++ B3910B A.03.27, HPUX)

X x1( f() ); : XC
X x2( g() ); : XCC
X const& x3 = f(); : X
X const& x4 = g(); : XC
------------------------------------------------------------------------

gcc does never (!) copy. Also the Microsoft compilers do avoid the
copy during return. They copy just the local variable. aCC on HPUX
does indeed copy during return. Because of this differences I would
not use this method of returning an object.

T.M.
Jul 23 '05 #9
Geo wrote:
You should consider returning a
std::auto_ptr, or some other smart pointer.


I agree with this advice. I recommend using a reference counting pointer
such as boost::shared_ptr for this. This will take care of memory
management automatically.

Regards
-Laurens
Jul 23 '05 #10
Torsten Mueller wrote:
gcc does never (!) copy.
The almost empty functions you wrote get inlined. Of course, if an
object is returned it must be copied and then it must be assigned to or
copied into another object (unless you use the returned temporary).
There is no black magic in C++.
Also the Microsoft compilers do avoid the
copy during return.
They copy just the local variable. aCC on HPUX
does indeed copy during return. Because of this differences I would
not use this method of returning an object.


.... and especially not because of a misleading example.

Jul 23 '05 #11
Panjandrum wrote:
Torsten Mueller wrote:
gcc does never (!) copy.
The almost empty functions you wrote get inlined.


gcc doesn't inline any functions unless optimizations are switched on.
Of course, if an object is returned it must be copied
No, NRVO can optimize that copy away.
and then it must be assigned to or copied into another object (unless you
use the returned temporary).
And also that copy can be optimized away, and gcc can do that.
There is no black magic in C++.


It's not black magic. It's a well-known optimization technique. Instead of
allocating the memory for the object locally in the called function, the
caller provides the memory and passes its address to the called function,
which then constructs the object directly into that memory, and so the
caller can use it without the need to copy it.
Jul 23 '05 #12
Rolf Magnus wrote:
Panjandrum wrote:
gcc doesn't inline any functions unless optimizations are switched on.
Of course, if an object is returned it must be copied


No, NRVO can optimize that copy away.


No! C and C++ programs consist of a stack of function calls. An object
that is returned to the calling function is copied (even with RVO).
Sorry, I don't have the nerve to argue with you any longer.

Jul 23 '05 #13
Panjandrum wrote:
Rolf Magnus wrote:
Panjandrum wrote:
gcc doesn't inline any functions unless optimizations are switched on.
Of course, if an object is returned it must be copied


No, NRVO can optimize that copy away.


No! C and C++ programs consist of a stack of function calls. An object
that is returned to the calling function is copied (even with RVO).
Sorry, I don't have the nerve to argue with you any longer.


Sorry, you are talking crap. The GCC result shows that the
object is never copied. If you run the following code, you will
see that the object always has the same address (not surprising
given that it is never copied). The C++ standard says that the
object does not need to be copied. What more evidence do you need?

#include <iostream>
using namespace std;

struct X
{
X() { cout << "X"; }
X( const X& ) { cout << "C"; }
};

X g()
{
X x;
cout << "[" << &x << "]";
return x;
}

#define TEST( code ) \
cout << #code << "\t: "; code; cout << endl

int main()
{
TEST( X x2( g() ); cout << &x2; );
TEST( X const& x4 = g(); cout << &x4; );
}

Jul 23 '05 #14
Me
> > > vector<int> f()
{
return vector<int>();
}


This will create a copy of the entire vector while the temporary
object will soon be forgotten unless the compiler supports a return
value optimization.


Even _with_ RVO

vector<int> x = f();

will copy the vector twice.


Wrong. At most it will do 1 default construction, 1 copy, and 2
destructions. With RVO it will just do 1 default construction and 1
destruction.

12.2/1 "Temporaries of class type are created in various contexts: ...
returning an rvalue"
6.6.3/2 "A return statement can involve the construction and copy of a
temporary object (12.2)."
8.5/14 "In certain cases, an implementation is permitted to eliminate
the copying inherent in this direct-initialization by constructing the
intermediate result directly into the object being initialized; see
12.2, 12.8."
12.8/15 "Whenever a temporary class object is copied using a copy
constructor, and this object and the copy have the same cv-unqualified
type, an implementation is permitted to treat the original and the copy
as two different ways of referring to the same object and not perform a
copy at all, even if the class copy constructor or destructor have side
effects."

Then 12.8 goes on to allow NRVO which is even more general than the
above code.

Jul 23 '05 #15
pmatos wrote:
Sometimes I have a function which creates an object and returns it.
Some are sets, other vectors but that's not very important.
In these cases I do something like this:

vector<int>* f(void) {
vector<int>* p = new vector<int>;
return p;
}
This is a bad idea.
Would there be any other way without pointers?

Would this work:

vector<int>& f(void) {
vector<int>* p = new vector<int>;
return *p;
}
And so is this.

Simply return by *value*:
cat f.cc

#include <vector>

std::vector<int> f(void) {
std::vector<int> v;
// modify v
return v;
}

Any decent optimizing C++ compiler will invoke
the Named Return Value Optimization (NRVO) --
the compiler recognizes v as a synonym for the return value
so that *no* copy is required!
Jul 23 '05 #16
Laurens wrote:
Geo wrote:
You should consider returning a std::auto_ptr,
or some other smart pointer.
I agree with this advice.


It's bad advice.
I recommend using a reference counting pointer
such as boost::shared_ptr for this.
This will take care of memory management automatically.


Nonsense!
The obvious best solution is to return by *value*.

Reference counting is routinely abused by C++ programmers.
It should be reserved for very special cases.
Objects that contain a reference counter can never truly be constants.
They not *thread safe*
and must be protected by [expensive] mutual exclusion
if they are used in threaded applications.
Jul 23 '05 #17
Torsten Mueller wrote:
I suggest to create the object outside the function.
You can use the function to fill it.

void f(std::vector<int>& v) {
// fill v ...
}


This is a bad idea and it is unnecessary.

C++ programmers should avoid functions that modify their arguments
but, if you *must* modify an argument, you should, at least,
return a reference to the modified argument:

std::vector<int>& f(std::vector<int>& v) {
// fill v
return v;
}

But the obvious solution here is to return by *value*:

std::vector<int> f(const size_t n) {
std::vector<int> v(n);
// fill v
return v;
}

Return by value simplifies code

const
std::vector<int> v = f(10);

and allows the application programmers to define constants
instead of compelling them to define variables
and initialize them in a second step.
The Named Return Value Optimization (NRVO)
allows the compiler to initialize v *directly*
from the call to f(10) *without* making any copies!
Jul 23 '05 #18
It's not black magic. It's a well-known optimization technique. Instead of
allocating the memory for the object locally in the called function, the
caller provides the memory and passes its address to the called function,
which then constructs the object directly into that memory, and so the
caller can use it without the need to copy it.


I wasn't aware of this, and if it's true, I'd certainly like to know more
about it. It'd be a very convenient thing.

You mean this? This I do all the time:

vector<int> & foobar(vector<int> & x)
{
// do stuff to x
return x;
}

int main()
{
vector<int> x(10000000);
x=foobar(x); // of course, = not necessary.
return 0;
}

This is trivial.

Or you mean it's all done transparently to the caller?

vector<int> foobar()
{
vector<int> x(10000000);
// do stuff to x
return x;
}

int main()
{
vector<int> x;
x=foobar();
return 0;
}

This indeed looks like voodoo. The vector::operator=() allocates the
necessary memory, and it does work with vector (I checked), but it
certainly doesn't work with valarray. You mean the compiler does all the
magic behind the scenes: it notices main::x will be allocated memory, and
that foo::x will no longer be needed after it's returned and assigned to
x, so it might as well use the same memory? That's pretty cool if the
compiler is that smart.

Using g++ 4.0, with -g -Wall. What optimization flags should I use to
avoid the copying? And how about valarray?
Jul 23 '05 #19
pmatos:

consider passing a pointer to a structure which contains every data
type you are in need of, along with a flag in the structure which
indicates which data type has been filled and therefore how to
process...

John

"pmatos" <po**@sat.inesc-id.pt> wrote in message
news:11**********************@g47g2000cwa.googlegr oups.com...
Hi all,

Sometimes I have a function which creates an object and returns it.
Some are sets, other vectors but that's not very important. In these
cases I do something like this:

vector<int> * f() {
vector<int> * v = new vector<int>;
return v;
}

Would there be any other way without pointers?

Would this work:
vector<int>& f() {
vector<int> v;
return v;
}

???

Cheers,

Paulo Matos

Jul 23 '05 #20
"E. Robert Tisdale" <E.**************@jpl.nasa.gov> schrieb:
I suggest to create the object outside the function.
You can use the function to fill it.
void f(std::vector<int>& v) {
// fill v ...
}
This is a bad idea and it is unnecessary.


Of course not. It avoids copying safely on *every* compiler.
C++ programmers should avoid functions that modify their arguments
but, if you *must* modify an argument, you should, at least, return
a reference to the modified argument:

std::vector<int>& f(std::vector<int>& v) {
// fill v
return v;
}
Why that? How is the return value related to the modified argument?
And what if there are two?

The only problem I see is to show the caller what's changed and what
is not. And this is just a question of strictly use of "const",
references and pointers in parameters. I use consequently const
references for constant parameters. If it's not const the caller can
be *sure* the parameter will be changed. It's very simple. I don't
understand any confusion about this. Mostly people are just too lazy
to use "const".
But the obvious solution here is to return by *value*:


No, returning by value is not a good idea having large objects and
applications being compiled with different compilers on several
platforms. I have a program on three platforms at the moment. I have
visible speed differences just because of such compiler dependent
stuff.

T.M.
Jul 23 '05 #21
Help me understand...
//g++-4.0.
#include <iostream>
#include <cstdlib>
#include <valarray>

using namespace std;

valarray<int> foo(int n)
{
valarray<int> x(n);
cerr << __FUNCTION__ << ": " << __LINE__ << ": "
<< &x << "\t" << x.size() << endl;
return x;
}

int main()
{
valarray<int> x=foo(3000);
valarray<int> y;

y = foo(2000);

cerr << __FUNCTION__ << ": " << __LINE__ << ": "
<< &x << "\t" << x.size() << endl;

cerr << __FUNCTION__ << ": " << __LINE__ << ": "
<< &y << "\t" << y.size() << endl;

return 0;
}

Jul 23 '05 #22
Amadeus W. M. wrote:
This indeed looks like voodoo.


The C++ Standard allows to elide 1 copy by RVO. That's all.

Jul 23 '05 #23
Amadeus W. M. wrote:
Help me understand...
//g++-4.0.
#include <iostream>
#include <cstdlib>
#include <valarray>

using namespace std;

valarray<int> foo(int n)
{
valarray<int> x(n);
cerr << __FUNCTION__ << ": " << __LINE__ << ": "
<< &x << "\t" << x.size() << endl;
return x;
}

int main()
{
valarray<int> x=foo(3000);
This is copy construction.
valarray<int> y;

y = foo(2000);
This is copy assignment, which can not be optimized away.

cerr << __FUNCTION__ << ": " << __LINE__ << ": "
<< &x << "\t" << x.size() << endl;

cerr << __FUNCTION__ << ": " << __LINE__ << ": "
<< &y << "\t" << y.size() << endl;

return 0;
}


Jul 23 '05 #24
Amadeus W. M. wrote:
It's not black magic. It's a well-known optimization technique.
Instead of allocating the memory for the object locally in the called function,
the caller provides the memory and passes its address to the called function,
which then constructs the object directly into that memory
so the caller can use it without the need to copy it.
I wasn't aware of this and, if it's true,
I'd certainly like to know more about it.


I used Google

http://www.google.com/

to search for

+"C++" +"NRVO"

and I found lots of stuff.
It'd be a very convenient thing.

You mean this? This I do all the time:

std::vector<int>& foobar(std::vector<int> & x) {
// do stuff to x
return x;
}

int main(int argc, char* argv[]) {
vector<int> x(10000000);
// x=foobar(x); // of course, = not necessary. foobar(x); // It's wrong. return 0;
}

This is trivial.

Or you mean it's all done transparently to the caller?

vector<int> foobar(void) {
vector<int> x(10000000);
// do stuff to x
return x;
}

int main(int argc, char* argv[]) {
vector<int> x = foobar(); // Use the copy constructor and *not* the assignment operator.
// The optimizer can elide the copy constructor
// but *not* the assignment operator. return 0;
}

This indeed looks like voodoo.
The vector::operator=() allocates the necessary memory
and it does work with vector (I checked)
but it certainly doesn't work with valarray.
You mean the compiler does all the magic behind the scenes:
it notices main::x will be allocated memory
and that foo::x will no longer be needed
after it's returned and assigned to x
so it might as well use the same memory?
You are confused.
You must avoid the assignment operator
and use the copy constructor instead.
That's pretty cool if the compiler is that smart.
All quality C++ compilers are that smart.
If your compiler does not implement the NRVO,
you should be shopping for a new C++ compiler
that does implement the NRVO.
Using g++ 4.0 with -g -Wall,
g++ -Wall -ansi -pedantic

Don't use the -g option unless you need to use the debugger.
What optimization flags should I use to avoid the copying?
And how about valarray?


The GNU C++ compiler, g++,
implements the Named Return Value Optimization (NRVO) by default.
Jul 23 '05 #25
Torsten Mueller wrote:
E. Robert Tisdale schrieb:

I suggest to create the object outside the function.
You can use the function to fill it.

void f(std::vector<int>& v) {
// fill v ...
}
This is a bad idea and it is unnecessary.


Of course not. It avoids copying safely on *every* compiler.
C++ programmers should avoid functions that modify their arguments
but, if you *must* modify an argument, you should, at least, return
a reference to the modified argument:

std::vector<int>& f(std::vector<int>& v) {
// fill v
return v;
}


Why that? How is the return value related to the modified argument?
And what if there are two?


I have just told you that
functions should *not* modify their arguments.
That goes double for two arguments. :-)

There are some exceptions
where operations must be performed "in place" on a variable object
but there is seldom any excuse for returning void.
You should always return something -- an exception (error code)
or a reference to the the object that was modified if nothing else.
This is a long standing tradition in C and C++.
Consider, for example, strcpy(char*, const char*)
which returns a pointer to the destination string or
operator<<(std::ostream&, int) which returns a reference
to the output stream which it modifies.
The only problem [that] I see
is to show the caller what's changed and what is not.
And this is just a question of strictly use of "const",
references and pointers in parameters.
Consequently, I use const references for constant parameters.
If it's not const the caller can be *sure* the parameter will be changed.
It's very simple.
I don't understand any confusion about this.
Mostly people are just too lazy to use "const".
But the obvious solution here is to return by *value*:


No, returning by value is not a good idea
[if you have] large objects and applications
being compiled with different compilers on several platforms.
I have a program on three platforms at the moment.
I have visible speed differences
just because of such compiler dependent stuff.


Using a bad C++ compiler is *not* a good excuse
for writing bad C++ code.
If your C++ compiler does not implement
the Named Return Value Optimization (NRVO),
you should be shopping for a new C++ compiler
that *does* implement the NRVO.

The market place is highly competitive
and quality implementations are available almost everywhere.
Inferior implementations should be discarded not coddled.
Jul 23 '05 #26
> I used Google

http://www.google.com/

to search for

+"C++" +"NRVO"
Funny. Ponder about your recommendation for a minute: how could I have
used google on something whose existence was not known to me? I did after
I read about it in this thread, of course.
You are confused.
You must avoid the assignment operator
and use the copy constructor instead.
Is this a commandment coming from a rocket scientist? Your advice is good,
and I don't mean any disrespect, but it would be better received if you
didn't speak in such a dismissive tone. People need to understand why, not
to be ordered.

And as a matter of fact, I know the constructor should be used and not the
assignment. However, constructing objects only upon the point when they
are needed (and parameters known), as opposed to declaring/constructing
them at the beginning of the function, confuses gdb, more often than not.

Using g++ 4.0 with -g -Wall,


g++ -Wall -ansi -pedantic

Don't use the -g option unless you need to use the debugger.


But I do. Doesn't everyone?

The GNU C++ compiler, g++,
implements the Named Return Value Optimization (NRVO) by default.


I figured, thanks!

Now NRVO works with the copy constructor only, and not with assignment. I
see no mention in the original post saying that he was going to use it
with the copy constructor. You're recommending something less general than
the scope of the original question, without even a warning, other than
"it's bad".

I realize that I've completely undermined my chances of ever working at
NASA.
Jul 23 '05 #27
Amadeus W. M. wrote:
Using g++ 4.0 with -g -Wall,


g++ -Wall -ansi -pedantic

Don't use the -g option unless you need to use the debugger.


But I do. Doesn't everyone?


I never use the debugger on code that I wrote.
I sometimes find it useful for analyzing code that other people wrote.
The GNU C++ compiler, g++,
implements the Named Return Value Optimization (NRVO) by default.


I figured, thanks!

Now NRVO works with the copy constructor only, and not with assignment.
I see no mention in the original post
saying that he was going to use it with the copy constructor.
You're recommending something less general than the scope of the original question
without even a warning, other than "it's bad".


This:

int main(int argc, char* argv[]) {
vector<int> x;
x = foobar();
return 0;
}

is bad. This:

int main(int argc, char* argv[]) {
vector<int> x = foobar();
return 0;
}

is better. And this:

int main(int argc, char* argv[]) {
const
vector<int> x = foobar();
return 0;
}

is better yet if you don't need to modify x in your program.
In general, you should avoid unnecessary program state variables
because they make your program more difficult to analyze
(read, understand and maintain).
Jul 23 '05 #28
Geo
E. Robert Tisdale wrote:
Using a bad C++ compiler is *not* a good excuse
for writing bad C++ code.
If your C++ compiler does not implement
the Named Return Value Optimization (NRVO),
you should be shopping for a new C++ compiler
that *does* implement the NRVO.

The market place is highly competitive
and quality implementations are available almost everywhere.
Inferior implementations should be discarded not coddled.


I guess working at NASA is similar to not living in the real world, I
would bet that most of us just don't have that choice.

Jul 23 '05 #29
"E. Robert Tisdale" <E.**************@jpl.nasa.gov> schrieb:
There are some exceptions where operations must be performed "in
place" on a variable object but there is seldom any excuse for
returning void.
What a beautiful dogma. Why that? It's just my decision to return
something or not.
You should always return something -- an exception (error code) or a
reference to the the object that was modified if nothing else. This
is a long standing tradition in C and C++.
Tradition is also to use int or char instead of bool.
Consider, for example, strcpy(char*, const char*) which returns a
pointer to the destination string or operator<<(std::ostream&, int)
which returns a reference to the output stream which it modifies.
These return values are for concatenation of multiple following
operations. They are useful.

I have a library of special string functions based on the STL string
class. These functions always return a string object. Nobody asks for
the time needed to create these temporary objects but everyone wonders
"It's not very fast, isn't it?". Nobody thinks about heap
fragmentation. Until now I eliminated more than two millions of
absolutely senseless string objects created in just one single minute
of runtime. Tell me, is this paradigma ("always return something")
useful in this case?

There is a lot of situations where indeed no result is to return,
where no result exists, where it needs just more time to create and to
evaluate the result than to return just nothing. Why the hell should a
sleep-function return something? And what?
Using a bad C++ compiler is *not* a good excuse for writing bad C++
code.
You can really be proud on you for knowing the bad and the good things
in the world. Have you ever been working on a system with a *given*
compiler, a compiler that cannot be changed for several reasons, a
compiler you just have to live with, and a manager who wants still a
good program?
If your C++ compiler does not implement the Named Return Value
Optimization (NRVO), you should be shopping for a new C++ compiler
that *does* implement the NRVO.


As long as I know how the compiler works and what I have to do to
write a quality program, a readable one, a fast one, a program that
runs on *any* compiler, I will do this. This is my profession. And my
profession is also to know these things rather than to assume every
compiler will surely do it right and fast.

I think it's not always a bad idea to change function parameters
especially if there are more than one. I use it seldom but sometimes
everything else would be just more complicated. I always mention it in
a comment. I name the function in that way

bool GetLoginValues (string& uid,string& pwd,string& host);

And I strictly use "const" for everything that *is* const. There's
nothing evil.

T.M.
Jul 23 '05 #30

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

11
by: Tom Leylan | last post by:
(I posted this in languages.vb also... I can't figure out where things go if you use a little of a lot of things) Hi all... I'm looking for an example (or a pointer to one) related to the...
0
by: Anonieko Ramos | last post by:
ASP.NET Forms Authentication Best Practices Dr. Dobb's Journal February 2004 Protecting user information is critical By Douglas Reilly Douglas is the author of Designing Microsoft ASP.NET...
13
by: andrea | last post by:
Sorry for the stupid question, I know, but sometimes is necessary starts from the basic. I don't know how to pass the result of a method generated from a DAL class to a BL class returning the...
13
by: frk.won | last post by:
I am interested in learning how to use the VS 2005 code snippets. However, I wish to know what are the best ways to source control the code snippets? Are there any source safe/subversion...
4
by: barcaroller | last post by:
I am trying to adopt a model for calling functions and checking their return values. I'm following Scott Meyer's recommendation of not over-using exceptions because of their potential overhead. ...
8
by: Palindrom | last post by:
Hi everyone ! I'd like to apologize in advance for my bad english, it's not my mother tongue... My girlfriend (who is a newbie in Python, but knows Perl quite well) asked me this morning why...
0
by: fig000 | last post by:
Hi, I'm using an objectdatasource. The insert procedure called by the objectdatasource is in a separate library file outside of the aspx and the codebehind that is using the objectdatasource in...
0
by: Charles Arthur | last post by:
How do i turn on java script on a villaon, callus and itel keypad mobile phone
0
by: aa123db | last post by:
Variable and constants Use var or let for variables and const fror constants. Var foo ='bar'; Let foo ='bar';const baz ='bar'; Functions function $name$ ($parameters$) { } ...
0
by: ryjfgjl | last post by:
If we have dozens or hundreds of excel to import into the database, if we use the excel import function provided by database editors such as navicat, it will be extremely tedious and time-consuming...
0
by: ryjfgjl | last post by:
In our work, we often receive Excel tables with data in the same format. If we want to analyze these data, it can be difficult to analyze them because the data is spread across multiple Excel files...
0
by: emmanuelkatto | last post by:
Hi All, I am Emmanuel katto from Uganda. I want to ask what challenges you've faced while migrating a website to cloud. Please let me know. Thanks! Emmanuel
0
BarryA
by: BarryA | last post by:
What are the essential steps and strategies outlined in the Data Structures and Algorithms (DSA) roadmap for aspiring data scientists? How can individuals effectively utilize this roadmap to progress...
1
by: Sonnysonu | last post by:
This is the data of csv file 1 2 3 1 2 3 1 2 3 1 2 3 2 3 2 3 3 the lengths should be different i have to store the data by column-wise with in the specific length. suppose the i have to...
0
marktang
by: marktang | last post by:
ONU (Optical Network Unit) is one of the key components for providing high-speed Internet services. Its primary function is to act as an endpoint device located at the user's premises. However,...
0
jinu1996
by: jinu1996 | last post by:
In today's digital age, having a compelling online presence is paramount for businesses aiming to thrive in a competitive landscape. At the heart of this digital strategy lies an intricately woven...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.