473,386 Members | 1,775 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,386 software developers and data experts.

*new or new?

It is better:
AnyClass &reg=*new AnyClass();
reg.Function();

or:
AnyClass *reg=new AnyClass();
reg->Function();

Thanks
Cristiano
Jul 22 '05 #1
30 1518
"Cristiano" <cr**********@NSquipo.it> wrote...
It is better:
AnyClass &reg=*new AnyClass();
reg.Function();

or:
AnyClass *reg=new AnyClass();
reg->Function();


For those two fragments the difference is only in the amount
of storage the program uses. The latter case _allocates_ some
storage for the pointer, and for the former it is unspecified
because it is up to the implementation whether references do
require storage.

Victor
Jul 22 '05 #2

"Cristiano" <cr**********@NSquipo.it> skrev i en meddelelse
news:P1******************@news3.tin.it...
It is better:
AnyClass &reg=*new AnyClass();
reg.Function();

or:
AnyClass *reg=new AnyClass();
reg->Function();

Thanks
Cristiano


The first form is obscure. How do you free the memory afterwards? Perhaps
you are confused, having programmed in Java (or C#) before. In this case the
alternatives are:
AnyClass reg;
reg.Function();

or:

AnyClass *reg=new AnyClass();
reg->Function();

If this is what you meant, You should always prefer the first case unless
compelled to do otherwise (and then you should prefer a smart pointer rather
than a raw one).

Kind regards
Peter
Jul 22 '05 #3
Peter Koch Larsen wrote:
"Cristiano" <cr**********@NSquipo.it> skrev i en meddelelse
news:P1******************@news3.tin.it...
It is better:
AnyClass &reg=*new AnyClass();
reg.Function();

or:
AnyClass *reg=new AnyClass();
reg->Function();
The first form is obscure. How do you free the memory afterwards?
Perhaps you are confused, [...]


Confused!? To free the memory you just need delete &reg.
In this case the alternatives are:

AnyClass reg;
reg.Function();
But this form is allocated into the stack (which usually is not too big).
or:

AnyClass *reg=new AnyClass();
reg->Function();


Which is what I wrote above and it is the form that I prefer.

Kind regards
Cristiano
Jul 22 '05 #4
Cristiano wrote:
Peter Koch Larsen wrote:
"Cristiano" <cr**********@NSquipo.it> skrev i en meddelelse
news:P1******************@news3.tin.it...
It is better:
AnyClass &reg=*new AnyClass();
reg.Function();

or:
AnyClass *reg=new AnyClass();
reg->Function();

Of those options, I prefer the first. I do something similar in certain
constructors, e.g.

template< typename T >
class C
{
T& m_t;

public:

C( ):
m_t( *new T )
{ }

~C( )
{
delete &m_t;
}
};

The first form is obscure. How do you free the memory afterwards?
Perhaps you are confused, [...]
I don't know about "obsure..."
Confused!? To free the memory you just need delete &reg.

In this case the alternatives are:

AnyClass reg;
reg.Function();

But this form is allocated into the stack (which usually is not too big).


Unless you have some particular reason to expect stack overflow,
Victor's right. Stack allocation is much faster and simpler than heap
allocation, and it avoids the need to call delete.
or:

AnyClass *reg=new AnyClass();
reg->Function();

Which is what I wrote above and it is the form that I prefer.

Kind regards
Cristiano


Jul 22 '05 #5
"Jeff Schwab" <je******@comcast.net> wrote...
Cristiano wrote:
Peter Koch Larsen wrote:
"Cristiano" <cr**********@NSquipo.it> skrev i en meddelelse
news:P1******************@news3.tin.it...

It is better:
AnyClass &reg=*new AnyClass();
reg.Function();

or:
AnyClass *reg=new AnyClass();
reg->Function(); [...]In this case the alternatives are:

AnyClass reg;
reg.Function();

But this form is allocated into the stack (which usually is not too

big).
Unless you have some particular reason to expect stack overflow,
Victor's right. Stack allocation is much faster and simpler than heap
allocation, and it avoids the need to call delete.


You mean, Peter Koch Larsen's right... I'd love to take credit, but can't.
Jul 22 '05 #6
Victor Bazarov wrote:
Unless you have some particular reason to expect stack overflow,
Victor's right. Stack allocation is much faster and simpler than heap
allocation, and it avoids the need to call delete.

You mean, Peter Koch Larsen's right... I'd love to take credit, but can't.


D'oh! Your post was right over Peter's in my reader; I should be more
careful. 20 bonus points for honesty, and my apologies to Peter.

-Jeff

Jul 22 '05 #7
"Jeff Schwab" <je******@comcast.net> wrote in message
news:X_********************@comcast.com...
Cristiano wrote:
Peter Koch Larsen wrote:
"Cristiano" <cr**********@NSquipo.it> skrev i en meddelelse
news:P1******************@news3.tin.it...

It is better:
AnyClass &reg=*new AnyClass();
reg.Function();

or:
AnyClass *reg=new AnyClass();
reg->Function();
Of those options, I prefer the first. I do something similar in certain
constructors, e.g.

template< typename T >
class C
{
T& m_t;

public:

C( ):
m_t( *new T )
{ }

~C( )
{
delete &m_t;
}
};
What is the advantage of this over the more obvious

template< typename T >
class C
{
T *m_t;
public:
C( ) : m_t(new T) { }
~C( ) {delete m_t;}
};

?

The first form is obscure. How do you free the memory afterwards?
Perhaps you are confused, [...]


I don't know about "obsure..."


Seems obscure to me. I don't usually think of a reference as a resource
which needs to be released.

[snip]

--
Cy
http://home.rochester.rr.com/cyhome/
Jul 22 '05 #8
Cy Edmunds wrote:
"Jeff Schwab" <je******@comcast.net> wrote in message
news:X_********************@comcast.com...
Cristiano wrote:
Peter Koch Larsen wrote:
"Cristiano" <cr**********@NSquipo.it> skrev i en meddelelse
news:P1******************@news3.tin.it...
>It is better:
> AnyClass &reg=*new AnyClass();
> reg.Function();
>
>or:
> AnyClass *reg=new AnyClass();
> reg->Function();


Of those options, I prefer the first. I do something similar in certain
constructors, e.g.

template< typename T >
class C
{
T& m_t;

public:

C( ):
m_t( *new T )
{ }

~C( )
{
delete &m_t;
}
};

What is the advantage of this over the more obvious

template< typename T >
class C
{
T *m_t;
public:
C( ) : m_t(new T) { }
~C( ) {delete m_t;}
};

?


More obvious to you, maybe, but not to me. :) The advantages are less
typing, better readability when the dynamically allocated object is
used, and the fact that '.' can't be overloaded (so I know exactly what
I'm getting). Mostly, I just think "object.method( )" looks nicer than
"object->method( )".

The first form is obscure. How do you free the memory afterwards?
Perhaps you are confused, [...]


I don't know about "obsure..."

Seems obscure to me. I don't usually think of a reference as a resource
which needs to be released.

[snip]


It's not. The dynamically allocated memory is. What difference does it
make, when you're using an object, how the object was allocated?

-Jeff

Jul 22 '05 #9
"Jeff Schwab" <je******@comcast.net> wrote in message
news:ot********************@comcast.com...
Cy Edmunds wrote:
"Jeff Schwab" <je******@comcast.net> wrote in message
news:X_********************@comcast.com...
Cristiano wrote:

Peter Koch Larsen wrote:
>"Cristiano" <cr**********@NSquipo.it> skrev i en meddelelse
>news:P1******************@news3.tin.it...
>
>
>>It is better:
>> AnyClass &reg=*new AnyClass();
>> reg.Function();
>>
>>or:
>> AnyClass *reg=new AnyClass();
>> reg->Function();

Of those options, I prefer the first. I do something similar in certain
constructors, e.g.

template< typename T >
class C
{
T& m_t;

public:

C( ):
m_t( *new T )
{ }

~C( )
{
delete &m_t;
}
};

What is the advantage of this over the more obvious

template< typename T >
class C
{
T *m_t;
public:
C( ) : m_t(new T) { }
~C( ) {delete m_t;}
};

?


More obvious to you, maybe, but not to me. :) The advantages are less
typing, better readability when the dynamically allocated object is
used, and the fact that '.' can't be overloaded (so I know exactly what
I'm getting). Mostly, I just think "object.method( )" looks nicer than
"object->method( )".


Me too. But that has nothing to do with it:

T &method() {return m_t;}

your way or

T &method() {return *m_t;}

mine. Any interface you can implement with a reference you can also
implement with a pointer. Thus the interface semantics are a moot point.

I will give an advantage to storing a pointer: it is closer to the intent of
the program. A pointer is generated in the constructor, stored in the class,
and deleted at destruction time. Converting it to a reference and then back
again just muddies up what is going on, making the program harder to
understand.

But it's a small point. Happy holidays.

>The first form is obscure. How do you free the memory afterwards?
>Perhaps you are confused, [...]

I don't know about "obsure..."

Seems obscure to me. I don't usually think of a reference as a resource
which needs to be released.

[snip]


It's not. The dynamically allocated memory is. What difference does it
make, when you're using an object, how the object was allocated?

-Jeff


--
Cy
http://home.rochester.rr.com/cyhome/
Jul 22 '05 #10

"Cy Edmunds" <ce******@spamless.rochester.rr.com> wrote in message
news:hl******************@twister.nyroc.rr.com...
"Jeff Schwab" <je******@comcast.net> wrote in message
news:ot********************@comcast.com...
Cy Edmunds wrote:
"Jeff Schwab" <je******@comcast.net> wrote in message
news:X_********************@comcast.com...


blah blah

You are all off course.
In general (i.e. more complicated class) the only exception safe
implementation is:

template<class T>
class C
{
std::auto_ptr<T> m;

C() : m(new T) {}
}

For one member it doesn't matter much but if you have 2 or more and the
ctors can throw then only auto_ptr will gaurantee that there are no leaks
e.g:

class C
{
T* m1; // or T&
T* m2; // or T&
C() : m1(new T), m2(new T) {}
~C();
};

If the ctor of the second T throws then ~C() will not be called and the
first T will be leaked.


Jul 22 '05 #11

"Nicholas Hounsome" <Nick nospace Hounsome @blueyonder.co.uk> skrev i en
meddelelse news:At*****************@news-binary.blueyonder.co.uk...

"Cy Edmunds" <ce******@spamless.rochester.rr.com> wrote in message
news:hl******************@twister.nyroc.rr.com...
"Jeff Schwab" <je******@comcast.net> wrote in message
news:ot********************@comcast.com...
Cy Edmunds wrote:
> "Jeff Schwab" <je******@comcast.net> wrote in message
> news:X_********************@comcast.com...

blah blah

You are all off course.
In general (i.e. more complicated class) the only exception safe
implementation is:


Of course - and i mentioned that in my original reply.

template<class T>
class C
{
std::auto_ptr<T> m;
However, it is by no means certain that a std::auto_ptr will serve your
needs, which is one of the reasons i did not elaborate on that aspect.

C() : m(new T) {}
}

For one member it doesn't matter much but if you have 2 or more and the
ctors can throw then only auto_ptr will gaurantee that there are no leaks
Your std::auto_ptr will not follow the same rules as the reference in the
original post. And now you will no longer be able to use your class as an
element in e.g. a std::vector. I would go for a boost::shared_ptr.
e.g:

class C
{
T* m1; // or T&
T* m2; // or T&
C() : m1(new T), m2(new T) {}
~C();
};

If the ctor of the second T throws then ~C() will not be called and the
first T will be leaked.

Kind regards
Peter
Jul 22 '05 #12
Jeff Schwab wrote:
Unless you have some particular reason to expect stack overflow,
Victor's right. Stack allocation is much faster and simpler than heap
allocation, and it avoids the need to call delete.


I should use that allocation for the big classes of C++ Builder. To allocate
them, it is suggested to use
TClass *MyClass = new TCLass()
instead of
TClass MyCLass.
(which sometimes doesn't work).

Thank you
Cristiano
Jul 22 '05 #13
"Nicholas Hounsome" <Nick nospace Hounsome @blueyonder.co.uk> wrote in
message news:At*****************@news-binary.blueyonder.co.uk...

"Cy Edmunds" <ce******@spamless.rochester.rr.com> wrote in message
news:hl******************@twister.nyroc.rr.com...
"Jeff Schwab" <je******@comcast.net> wrote in message
news:ot********************@comcast.com...
Cy Edmunds wrote:
> "Jeff Schwab" <je******@comcast.net> wrote in message
> news:X_********************@comcast.com...

blah blah

You are all off course.
In general (i.e. more complicated class) the only exception safe
implementation is:

template<class T>
class C
{
std::auto_ptr<T> m;

C() : m(new T) {}
}

For one member it doesn't matter much but if you have 2 or more and the
ctors can throw then only auto_ptr will gaurantee that there are no leaks


No, there are other ways.
e.g:

class C
{
T* m1; // or T&
T* m2; // or T&
C() : m1(new T), m2(new T) {}
~C();
};

If the ctor of the second T throws then ~C() will not be called and the
first T will be leaked.


Classes which contain std::auto_ptr get the strange copy semantics of
std::auto_ptr. That's why I would never put one in a class. For instance:

C x, y;
x = y; // changes x AND y!

This is too weird to let loose on the world. I don't care what the
documentation says.

In the previous discussion we were only considering how to store the
pointer, not the design of a complete class. The Rule of Three tells us that
if a class has a destructor, a copy constructor, or an assignment operator
it almost certainly needs all three. Thus the classes we were talking about
had worse problems than exception safety -- you couldn't even copy one
safely. There are two solutions to this which provide exception safety while
supporting normal copying semantics:

1) include a proper copy constructor and assignment operator
2) wrap the pointer in a reference counted smart pointer and get rid of the
destructor

The first solution is much harder to do correctly than the second, but it
certainly can be done.

--
Cy
http://home.rochester.rr.com/cyhome/
Jul 22 '05 #14
Cristiano wrote:
Jeff Schwab wrote:
Unless you have some particular reason to expect stack overflow,
Victor's right. Stack allocation is much faster and simpler than heap
allocation, and it avoids the need to call delete.

I should use that allocation for the big classes of C++ Builder. To allocate
them, it is suggested to use
TClass *MyClass = new TCLass()
instead of
TClass MyCLass.
(which sometimes doesn't work).


It sure sounds like the implementers had a reason to expect overflow. :)
Have you actually seen "TClass MyClass" fail?

Jul 22 '05 #15
Jeff Schwab wrote:
Cristiano wrote:
Jeff Schwab wrote:
Unless you have some particular reason to expect stack overflow,
Victor's right. Stack allocation is much faster and simpler than
heap allocation, and it avoids the need to call delete.

I should use that allocation for the big classes of C++ Builder. To
allocate them, it is suggested to use
TClass *MyClass = new TCLass()
instead of
TClass MyCLass.
(which sometimes doesn't work).


It sure sounds like the implementers had a reason to expect overflow.
:)
Have you actually seen "TClass MyClass" fail?


No. MyClass doesn't exist.
When I try to compile TRegistry reg I get: "VCL style classes must be
constructed using operator new" and the compiler stops.

Cristiano
Jul 22 '05 #16
Cristiano wrote:
It is better:
AnyClass &reg=*new AnyClass();
reg.Function();

or:

AnyClass *pReg=new AnyClass();
pReg->Function();


AnyClass reg;
reg.Function();

is best.

But, if you must allocate storage from the free store,
the first is *always* preferred
unless the "reference" must be "reseated" later.

Jul 22 '05 #17

"E. Robert Tisdale" <E.**************@jpl.nasa.gov> wrote in message
news:3F**************@jpl.nasa.gov...
Cristiano wrote:
It is better:
AnyClass &reg=*new AnyClass();
reg.Function();

or:

AnyClass *pReg=new AnyClass();
> pReg->Function();
AnyClass reg;
reg.Function();

is best.

But, if you must allocate storage from the free store,
the first is *always* preferred


by you.
unless the "reference" must be "reseated" later.


What about freeing the storage?
No delete - leaks.
delete &reg - leaves an invalid reference
Jul 22 '05 #18
Nick Hounsome wrote:
"E. Robert Tisdale" <E.**************@jpl.nasa.gov> wrote in message
news:3F**************@jpl.nasa.gov...
Cristiano wrote:

It is better:
AnyClass &reg=*new AnyClass();
reg.Function();

or:

AnyClass *pReg=new AnyClass();

> pReg->Function();


AnyClass reg;
reg.Function();

is best.

But, if you must allocate storage from the free store,
the first is *always* preferred

by you.

unless the "reference" must be "reseated" later.

What about freeing the storage?
No delete - leaks.
delete &reg - leaves an invalid reference


Just as delete pReg leaves a pointer to an invalid address.

It seems to me that the difference between these two notations is mostly
aesthetic. The only "real" difference I see is that -> can be
overloaded, whereas . cannot. Either might be preferable, according to
circumstance.

If somebody can come up with a part of the Standard that prefers one of
these notations to the other, I'll be interested to read it.

-Jeff

Jul 22 '05 #19

"Jeff Schwab" <je******@comcast.net> wrote in message
news:-t********************@comcast.com...
Nick Hounsome wrote:
"E. Robert Tisdale" <E.**************@jpl.nasa.gov> wrote in message
news:3F**************@jpl.nasa.gov...
Cristiano wrote:
It is better:
AnyClass &reg=*new AnyClass();
reg.Function();

or:

AnyClass *pReg=new AnyClass();

> pReg->Function();

AnyClass reg;
reg.Function();

is best.

But, if you must allocate storage from the free store,
the first is *always* preferred

by you.

unless the "reference" must be "reseated" later.

What about freeing the storage?
No delete - leaks.
delete &reg - leaves an invalid reference


Just as delete pReg leaves a pointer to an invalid address.


There is a difference - the pointer can be set to 0 and subsequently tested.
Indeed it is common to write stuff like:
if( !p ) p = new P();
There is no equivalent for references.
It seems to me that the difference between these two notations is mostly
aesthetic. The only "real" difference I see is that -> can be
overloaded, whereas . cannot. Either might be preferable, according to
circumstance.
The advantage of references is the gaurantee (in the absence of people dong
the above) that the reference is valid.
This is very helpful when dealing with analy retentive coding standards that
insist that you check all pointers for null on entry.

One advantage of pointers is that you can put them in an auto_ptr and forget
them. (Of course you could write an equivalent for your references).
Another is that you can use 0 to mean something - either as a parameter when
it usualy means 'use defaults' or as a member when it means 'not yet
initialized'

If somebody can come up with a part of the Standard that prefers one of
these notations to the other, I'll be interested to read it.
I have found a more serious argument: consider

AnyClass& reg=*new DerivedFromAnyClass();

The standard states that the implementation can (implementation defined)
bind to the AnyClass subobject of a temporary copy.
This would obviously be a disaster since the original would leak and delete
&reg would try to deallocate something on the stack.

P.S. The equivalent to
AnyClass& reg=*new AnyClass();
is
AnyClass * const pReg=new AnyClass();
not
AnyClass *pReg=new AnyClass();

Because the latter can be rebound unlike the reference
-Jeff

Jul 22 '05 #20

"Nick Hounsome" <nh***@blueyonder.co.uk> wrote in message news:d2******************@news-binary.blueyonder.co.uk...
The advantage of references is the gaurantee (in the absence of people dong
the above) that the reference is valid.
This is very helpful when dealing with analy retentive coding standards that
insist that you check all pointers for null on entry.
Of course, that just moves the undefined behavior around. If someone was
likely to have passed a null pointer to a function unprepared to handle it, he was
probably just as likely to dereference it in his code and pass you a reference to
a "null" object.


The issue is not pointer versus reference so much as dynamic versus non-dynamic
storage duration. The latter is clearly preferable, and even dynamic storage is
better off handled by wrapping it in some non-dynamic class.

Jul 22 '05 #21

"Ron Natalie" <ro*@sensor.com> wrote in message
news:3f***********************@news.newshosting.co m...

"Nick Hounsome" <nh***@blueyonder.co.uk> wrote in message news:d2******************@news-binary.blueyonder.co.uk...
The advantage of references is the gaurantee (in the absence of people dong the above) that the reference is valid.
This is very helpful when dealing with analy retentive coding standards that insist that you check all pointers for null on entry.


Of course, that just moves the undefined behavior around. If someone was
likely to have passed a null pointer to a function unprepared to handle

it, he was probably just as likely to dereference it in his code and pass you a reference to a "null" object.
You miss the point - I don't have to check references even if they are bad
because there is no way to check them hence my code isn't littered with
tests that obscure the logic.


The issue is not pointer versus reference so much as dynamic versus

non-dynamic storage duration. The latter is clearly preferable, and even dynamic storage is better off handled by wrapping it in some non-dynamic class.


reference to dynamic is not the same as non-dynamic.

The wrapper for dynamic is calld std::auto_ptr

Jul 22 '05 #22
Nick Hounsome wrote:
"Jeff Schwab" <je******@comcast.net> wrote in message
news:-t********************@comcast.com...
Nick Hounsome wrote:
"E. Robert Tisdale" <E.**************@jpl.nasa.gov> wrote in message
news:3F**************@jpl.nasa.gov...
Cristiano wrote:

>It is better:
> AnyClass &reg=*new AnyClass();
> reg.Function();
>
>or:
>
> AnyClass *pReg=new AnyClass();

> pReg->Function();

AnyClass reg;
reg.Function();

is best.

But, if you must allocate storage from the free store,
the first is *always* preferred
by you.

unless the "reference" must be "reseated" later.

What about freeing the storage?
No delete - leaks.
delete &reg - leaves an invalid reference
Just as delete pReg leaves a pointer to an invalid address.

There is a difference - the pointer can be set to 0 and subsequently tested.
Indeed it is common to write stuff like:
if( !p ) p = new P();
There is no equivalent for references.


That's not what the OP was doing. References and pointers are *not* the
same thing; however, I know of no problem with binding *new to a
reference, and your example does not demonstrate one. It only shows a
pointer being used in a way that a reference cannot. Often, references
make more sense than pointers for this sort of thing. For example, it
is common to have a member pointer to some memory allocated by the
constructor. In this case, the memory typically is deallocated in the
destructor, and there is no point in resetting the pointer to null. In
fact, I find references preferable to pointers in this case, since you
will get a compile-time error if you forget to allocate the memory. If
you forget to initialize the pointer, the error will not occur until
run-time; such bugs can be horribly pernicious.
It seems to me that the difference between these two notations is mostly
aesthetic. The only "real" difference I see is that -> can be
overloaded, whereas . cannot. Either might be preferable, according to
circumstance.

The advantage of references is the gaurantee (in the absence of people dong
the above) that the reference is valid.


There is no such guarantee.
This is very helpful when dealing with analy retentive coding standards that
insist that you check all pointers for null on entry.
Blame the coding standard, not the initialiation of references with
dynamically allocated memory.
One advantage of pointers is that you can put them in an auto_ptr and forget
them. (Of course you could write an equivalent for your references).
Another is that you can use 0 to mean something - either as a parameter when
it usualy means 'use defaults' or as a member when it means 'not yet
initialized'
Yes, pointers certainly have the advantage over references in many (but
not all) cases.
If somebody can come up with a part of the Standard that prefers one of
these notations to the other, I'll be interested to read it.


I have found a more serious argument: consider

AnyClass& reg=*new DerivedFromAnyClass();

The standard states that the implementation can (implementation defined)
bind to the AnyClass subobject of a temporary copy.
This would obviously be a disaster since the original would leak and delete
&reg would try to deallocate something on the stack.


Only if the destructor is non-virtual. The same argument can be made
against pointers. This is not a reference-specific problem.
P.S. The equivalent to
AnyClass& reg=*new AnyClass();
is
AnyClass * const pReg=new AnyClass();
not
AnyClass *pReg=new AnyClass();

Because the latter can be rebound unlike the reference


Again, the OP was not looking to "rebind the reference." You've
mentioned cases where pointers are needed. If your point is that
references cannot entirely replace pointers, I wholeheartedly agree.
However, I still see nothing wrong with either of the OP's offerings.

-Jeff

Jul 22 '05 #23

"Jeff Schwab" <je******@comcast.net> wrote in message
news:6d********************@comcast.com...
[]

I have found a more serious argument: consider

AnyClass& reg=*new DerivedFromAnyClass();

The standard states that the implementation can (implementation defined)
bind to the AnyClass subobject of a temporary copy.
This would obviously be a disaster since the original would leak and delete &reg would try to deallocate something on the stack.


Only if the destructor is non-virtual. The same argument can be made
against pointers. This is not a reference-specific problem.


No - the standard says (goodness knows why) that this can be implemented as:

DerivedFromAnyClass temp = *new DerivedFromAnyClass();
AnyClass& reg = temp;

i.e. regardless of virtual dtors the dynamically allocated object is leaked
and
delete &reg trys to free a non-heap object.
Jul 22 '05 #24
Nick Hounsome wrote:
"Jeff Schwab" <je******@comcast.net> wrote in message
news:6d********************@comcast.com...
[]
I have found a more serious argument: consider

AnyClass& reg=*new DerivedFromAnyClass();

The standard states that the implementation can (implementation defined)
bind to the AnyClass subobject of a temporary copy.
This would obviously be a disaster since the original would leak and
delete
&reg would try to deallocate something on the stack.


Only if the destructor is non-virtual. The same argument can be made
against pointers. This is not a reference-specific problem.

No - the standard says (goodness knows why) that this can be implemented as:

DerivedFromAnyClass temp = *new DerivedFromAnyClass();
AnyClass& reg = temp;

i.e. regardless of virtual dtors the dynamically allocated object is leaked
and
delete &reg trys to free a non-heap object.


Wow, that's news to me. Do you happen to know of any compilers that
actually do that? This is fine in GCC:

/* Output is:
* ~B
* ~A
*/
#include <iostream>

struct A { virtual ~A( ) { std::cerr << "~A\n"; } };
struct B: A { ~B( ) { std::cerr << "~B\n"; } };

int main( )
{
A& a = *new B;

delete &a;
}

Jul 22 '05 #25
Nick Hounsome wrote:
"Jeff Schwab" <je******@comcast.net> wrote in message
news:6d********************@comcast.com...
[]
I have found a more serious argument: consider

AnyClass& reg=*new DerivedFromAnyClass();

The standard states that the implementation can (implementation defined)
bind to the AnyClass subobject of a temporary copy.
This would obviously be a disaster since the original would leak and
delete
&reg would try to deallocate something on the stack.


Only if the destructor is non-virtual. The same argument can be made
against pointers. This is not a reference-specific problem.

No - the standard says (goodness knows why) that this can be implemented as:

DerivedFromAnyClass temp = *new DerivedFromAnyClass();
AnyClass& reg = temp;


Btw, what section of the standard is this?

Thanks,
Jeff

Jul 22 '05 #26

"Jeff Schwab" <je******@comcast.net> wrote in message news:y8********************@comcast.com...
int main( )
{
A& a = *new B;

delete &a;


The original premise is wrong. &a is NOT a heap object. It's the legitimate address
of the A subobject of the dynamically allocated B.

Jul 22 '05 #27

"Ron Natalie" <ro*@sensor.com> wrote in message news:3f***********************@news.newshosting.co m...

"Jeff Schwab" <je******@comcast.net> wrote in message news:y8********************@comcast.com...
int main( )
{
A& a = *new B;

delete &a;


The original premise is wrong. &a is NOT a heap object.

Gak...that should read &a IS a heap object. It is not a STACK object.

Jul 22 '05 #28

"Jeff Schwab" <je******@comcast.net> wrote in message
news:4Z********************@comcast.com...
Nick Hounsome wrote:
"Jeff Schwab" <je******@comcast.net> wrote in message
news:6d********************@comcast.com...
[]
I have found a more serious argument: consider

AnyClass& reg=*new DerivedFromAnyClass();

The standard states that the implementation can (implementation defined)bind to the AnyClass subobject of a temporary copy.
This would obviously be a disaster since the original would leak and
delete
&reg would try to deallocate something on the stack.

Only if the destructor is non-virtual. The same argument can be made
against pointers. This is not a reference-specific problem.

No - the standard says (goodness knows why) that this can be implemented as:
DerivedFromAnyClass temp = *new DerivedFromAnyClass();
AnyClass& reg = temp;


Btw, what section of the standard is this?


reference is 8.5.3 para 5

On closer inspection I think it is only a problem if the cv qualifiers
differ i.e.
const AnyClass& reg = *new DerivedFromAnyClass;
or is it
AnyClass& reg = *new const DerivedFromAnyClass; ????

but then that just confirms my general approach which is not to delve into
unusual corners of the language where you need to check the standard unless
strictly necessary.
Thanks,
Jeff

Jul 22 '05 #29
Ron Natalie wrote:
"Ron Natalie" <ro*@sensor.com> wrote in message news:3f***********************@news.newshosting.co m...
"Jeff Schwab" <je******@comcast.net> wrote in message news:y8********************@comcast.com...

int main( )
{
A& a = *new B;

delete &a;


The original premise is wrong. &a is NOT a heap object.


Gak...that should read &a IS a heap object. It is not a STACK object.


Did someone imply otherwise? Do you know of anything wrong with the
above code?

Jul 22 '05 #30
I would always go for number 2.

First of all, you are allocating a pointer.

Why in the world would you want to create a reference to it without
keeping track of what is the memory location of this pointer?

Who will handle the memory deallocation of your newly allocate pointer?

By the way, have you thought of doing?

std::auto_ptr<AnyClass> reg(new AnyClass());
*reg.Function();

E. Robert Tisdale wrote:
Cristiano wrote:
It is better:
AnyClass &reg=*new AnyClass();
reg.Function();

or:

AnyClass *pReg=new AnyClass();

> pReg->Function();


AnyClass reg;
reg.Function();

is best.

But, if you must allocate storage from the free store,
the first is *always* preferred
unless the "reference" must be "reseated" later.

Jul 22 '05 #31

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

Similar topics

1
by: Nimmi Srivastav | last post by:
There's a rather nondescript book called "Using Borland C++" by Lee and Mark Atkinson (Que Corporation) which presents an excellent discussion of overloaded new and delete operators. In fact there...
3
by: Nimmi Srivastav | last post by:
There's a rather nondescript book called "Using Borland C++" by Lee and Mark Atkinson (Que Corporation) which presents an excellent discussion of overloaded new and delete operators. I am...
5
by: | last post by:
Hi all, I've been using C++ for quite a while now and I've come to the point where I need to overload new and delete inorder to track memory and probably some profiling stuff too. I know that...
2
by: Dave | last post by:
Hello all, I'd like to find a source on the web that discusses, in a comprehensive manner and in one place, everything about new / delete. It should include overloading operator new, the new...
15
by: Steve | last post by:
I have a form with about 25 fields. In the BeforeUpdate event of the form, I have code that sets the default value of each field to its current value. For a new record, I can put the focus in any...
7
by: Mike Bulava | last post by:
I have created a base form that I plan to use throughout my application let call the form form1. I have Built the project then add another form that inherits from form1, I add a few panel controls...
7
by: Sakharam Phapale | last post by:
Hi All, How to preserve the old font properties while changing new one? I posted same question 2 months back, but I had very small time then. eg. "Shopping for" is a text in RichTextBox and...
0
by: Ben | last post by:
module main ... application.run(new splashform) .. end module after a few screen, I try to load a new codes I got from MSDN on datagrid that works on its own. I took out submain and ran...
3
by: Grizlyk | last post by:
Hi, people. Can anybody explain me "multiple 'new' at single line" behavior. Consider: p::p(void*); p::p(void*,void*); new A( p(new B), p( new C(p(new D), p(new E)) ), p(new F));
4
by: rgparkins | last post by:
Hello I am running out of time with a problem I have running PHP 5.04 and Apache 2.0 and really need help :(. I have a page that stores a variable in session but each time I reload that page the...
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:
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
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
by: Hystou | last post by:
There are some requirements for setting up RAID: 1. The motherboard and BIOS support RAID configuration. 2. The motherboard has 2 or more available SATA protocol SSD/HDD slots (including MSATA, M.2...
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
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can...
0
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers,...
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.