Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C++ > operator= could not be generated

Reply
Thread Tools

operator= could not be generated

 
 
Jeffrey Walton
Guest
Posts: n/a
 
      07-08-2010
Hi All,

I'm working with some C++ code that performs a lot of heap allocations
on typef'd structs, structs, and classes, but does not ensure cleanup.
Many of the classes and structs hide their assignment operator.

I attempted to write a template class to ensure cleanup, but am
receiving the error, "operator= could not be generated".

Two questions. (1) I'm dealting with pointers and not objects. So why
is an assignmnet operator needed? (2) I know the void* hack is
bullshit. How do I accomplish my goals of the delete, and then set the
pointer to NULL.

Thanks,
Jeff

template <class T>
PtrTypeCleanup<T>:trTypeCleanup(T*& ptr)
: m_ptr(NULL)
{
// Most types have their assignment operator hidden.
// Cast so that we can set the bastard to NULL.
reinterpret_cast<void*>(m_ptr) = reinterpret_cast<void*>(ptr);
}

template <class T>
PtrTypeCleanup<T>::~PtrTypeCleanup(void)
{
if(m_ptr)
{
// We must delete through the type
delete m_ptr;
// Most types have their assignment operator hidden.
// Cast so that we can set the bastard to NULL.
// void* p = reinterpret_cast<void*>(m_ptr);
// p = NULL;
}
}

template <class T>
void PtrTypeCleanup<T>::Release(void)
{
// Most types have their assignment operator hidden.
// Cast so that we can set the bastard to NULL.
// void* p = reinterpret_cast<void*>(m_ptr);
// p = NULL;
}

template <class T>
T*& PtrTypeCleanup<T>:perator=(const T*& rhs)
{
// No self assignment
if(this == &rhs) { return *this; }

reinterpret_cast<void*>(m_ptr) =
reinterpret_cast<void*>(rhs.m_ptr);
}

 
Reply With Quote
 
 
 
 
Victor Bazarov
Guest
Posts: n/a
 
      07-08-2010
On 7/8/2010 4:23 PM, Jeffrey Walton wrote:
> I'm working with some C++ code that performs a lot of heap allocations
> on typef'd structs, structs, and classes, but does not ensure cleanup.
> Many of the classes and structs hide their assignment operator.
>
> I attempted to write a template class to ensure cleanup, but am
> receiving the error, "operator= could not be generated".


Error? Are you sure? Not a warning?

> Two questions. (1) I'm dealting with pointers and not objects. So why
> is an assignmnet operator needed?


Usually the assignment operator is used when you *assign* to the object
of your class. Since you didn't post any code showing how you operate
on your objects (of type PtrTypeCleanup), I can't be more specific.
Please see FAQ 5.8.

> (2) I know the void* hack is
> bullshit. How do I accomplish my goals of the delete, and then set the
> pointer to NULL.


Deleting and setting WHAT to NULL? 'm_ptr'? How is it declared?

> [..]


The assignment operator cannot be generated usually if your class has a
member with an inaccessible assignment operator, or a constant data
member, etc., IOW a member which does not have assignment semantics.

Since you elected not to post the definition of your class, I can't be
more specific. Please see FAQ 5.8.

V
--
I do not respond to top-posted replies, please don't ask
 
Reply With Quote
 
 
 
 
Jeffrey Walton
Guest
Posts: n/a
 
      07-08-2010
Hi Victor,

My apologies again. I missed another detail.....

On Jul 8, 4:52*pm, Victor Bazarov <(E-Mail Removed)> wrote:
> On 7/8/2010 4:23 PM, Jeffrey Walton wrote:
>
> > I'm working with some C++ code that performs a lot of heap allocations
> > on typef'd structs, structs, and classes, but does not ensure cleanup.
> > Many of the classes and structs hide their assignment operator.

>
> > [SNIP]

>
> > Two questions. (1) I'm dealting with pointers and not objects. So why
> > is an assignmnet operator needed?

>
> Usually the assignment operator is used when you *assign* to the object
> of your class. *Since you didn't post any code showing how you operate
> on your objects (of type PtrTypeCleanup), I can't be more specific.

Here's how this might be used:

CSomeClass* someClass = new someClass;
PtrTypeCleanup<CSomeClass> cleanup(someClass);

// Do useful things with someClass. Upon an exception,
// I'm ensured the class is cleaned up. I'm also ensured
// that the original pointer is NULL in an attempt to
// vet pointer reuse.

Recall from my statement above, CSomeClass might (and probably does)
have a hidden operator=.

> Please see FAQ 5.8.

I cringe when I have to do anything with this solution. There are
nearly 900 source files which produce 7 executable modules with
everything inter-twinded. I probably could not give you a concrete
example without including at least 20 source files.

Do you really need concrete examples that compile and link for an
abstract question? Ie, why do I need an operator= when I'm dealing
with pointers.

>
> *[SNIP]


Jeff
 
Reply With Quote
 
Jonathan Lee
Guest
Posts: n/a
 
      07-08-2010
On Jul 8, 5:48*pm, Jeffrey Walton <(E-Mail Removed)> wrote:
> Here's how this might be used:
>
> CSomeClass* someClass = new someClass;
> PtrTypeCleanup<CSomeClass> cleanup(someClass);
>
> // Do useful things with someClass. Upon an exception,
> // I'm ensured the class is cleaned up. I'm also ensured
> // that the original pointer is NULL in an attempt to
> // vet pointer reuse.


If you can change your usage pattern slightly you
could probably get away with using std::auto_ptr or
one of the Boost smart pointers.

Specifically, I think you're going to have a lot of
problems with trying to clear the original pointer.
A better pattern might be

auto_ptr<CSomeClass> cleanup(new CSomeClass);
CSomeClass* someClass = cleanup.get();

In this arrangement, you don't have to actually set
someClass to null. It has a shorter lifetime than
cleanup (unless you reset cleanup or something).

I don't see where operator= enters into it, since
you're assigning pointers, not objects.

--Jonathan
 
Reply With Quote
 
James Kanze
Guest
Posts: n/a
 
      07-09-2010
On Jul 8, 9:23 pm, Jeffrey Walton <(E-Mail Removed)> wrote:
> I'm working with some C++ code that performs a lot of heap allocations
> on typef'd structs, structs, and classes, but does not ensure cleanup.
> Many of the classes and structs hide their assignment operator.


> I attempted to write a template class to ensure cleanup, but am
> receiving the error, "operator= could not be generated".


> Two questions. (1) I'm dealting with pointers and not objects. So why
> is an assignmnet operator needed? (2) I know the void* hack is
> bullshit. How do I accomplish my goals of the delete, and then set the
> pointer to NULL.


I'm not quite sure what you're trying to accomplish, but.../

> template <class T>
> PtrTypeCleanup<T>:trTypeCleanup(T*& ptr)
> : m_ptr(NULL)
> {
> // Most types have their assignment operator hidden.
> // Cast so that we can set the bastard to NULL.
> reinterpret_cast<void*>(m_ptr) = reinterpret_cast<void*>(ptr);


This shouldn't compile. The result of a reinterpret_cast is an
rvalue, and the left hand operand of the built-in assignment
operator requires an lvalue.

> }


> template <class T>
> PtrTypeCleanup<T>::~PtrTypeCleanup(void)
> {
> if(m_ptr)
> {
> // We must delete through the type
> delete m_ptr;
> // Most types have their assignment operator hidden.
> // Cast so that we can set the bastard to NULL.
> // void* p = reinterpret_cast<void*>(m_ptr);
> // p = NULL;
> }
> }


> template <class T>
> void PtrTypeCleanup<T>::Release(void)
> {
> // Most types have their assignment operator hidden.
> // Cast so that we can set the bastard to NULL.
> // void* p = reinterpret_cast<void*>(m_ptr);
> // p = NULL;
> }


> template <class T>
> T*& PtrTypeCleanup<T>:perator=(const T*& rhs)
> {
> // No self assignment
> if(this == &rhs) { return *this; }
>
> reinterpret_cast<void*>(m_ptr) = reinterpret_cast<void*>(rhs.m_ptr);
> }


Can we see the complete definition of PtrTypeCleanup, and
possibly an example of its use? As it is, I'm not quite clear
what it is supposed to be doing. (Something like
boost::scoped_ptr, but with an additional level of indirection
on the pointer?)

--
James Kanze
 
Reply With Quote
 
James Kanze
Guest
Posts: n/a
 
      07-09-2010
On Jul 8, 10:48 pm, Jeffrey Walton <(E-Mail Removed)> wrote:
> On Jul 8, 4:52 pm, Victor Bazarov <(E-Mail Removed)> wrote:> On 7/8/2010 4:23 PM, Jeffrey Walton wrote:


[...]
> Here's how this might be used:


> CSomeClass* someClass = new someClass;
> PtrTypeCleanup<CSomeClass> cleanup(someClass);


And you want the destructor of cleanup to delete the object?
And maybe clear the pointer. What's wrong with simply:

template<typename T>
class PtrTypeCleanup : boost::noncopiable
{
T*& m_watched;
public:
explicit PtrTypeCleanup(T* clientPtr)
: m_watched(clientPtr) {}
~PtrTypeCleanup()
{
delete m_watched;
m_watched = NULL; // If desired.
}
};

> // Do useful things with someClass. Upon an exception,
> // I'm ensured the class is cleaned up. I'm also ensured
> // that the original pointer is NULL in an attempt to
> // vet pointer reuse.


> Recall from my statement above, CSomeClass might (and probably does)
> have a hidden operator=.


What CSomeClass has is pretty much irrelevant here (although
mostly objects that you allocation dynamically don't support
assignment).

--
James Kanze
 
Reply With Quote
 
Jorgen Grahn
Guest
Posts: n/a
 
      07-20-2010
On Thu, 2010-07-08, Jeffrey Walton wrote:

> On Jul 8, 4:52*pm, Victor Bazarov <(E-Mail Removed)> wrote:

....
>> Please see FAQ 5.8.

> I cringe when I have to do anything with this solution. There are
> nearly 900 source files which produce 7 executable modules with
> everything inter-twinded. I probably could not give you a concrete
> example without including at least 20 source files.


I think he expects you to edit it down as needed, not just show a
subset of your solution's files verbatim.

> Do you really need concrete examples that compile and link for an
> abstract question? Ie, why do I need an operator= when I'm dealing
> with pointers.


I suspect that he suspect that you are focusing on the wrong thing,
and that your problem is in the parts you're not showing. Half the
questions posted here these days are like that.

And also your question is based on an impossible premise. You *don't*
need Foo:perator=() if all you do is mess with Foo pointers. All you
need is, I think, the single forward declaration "class Foo;".

/Jorgen

--
// Jorgen Grahn <grahn@ Oo o. . .
\X/ snipabacken.se> O o .
 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
Could not connect to mail server System.Web Could not access 'CDO.Message' object. ????? Adam Knight ASP .Net 1 12-05-2005 05:38 AM
vb.net mod fails 'app has generated an exception that could not be =?Utf-8?B?QmlsbA==?= ASP .Net 0 04-10-2005 09:55 PM
Error Message: Outlook Express Could Not Be Started Because Msoe.dll Could Not Be Loaded Dutch Treat Computer Support 4 06-21-2004 02:01 PM
Re: Application has generated an exception that could not be handled Peter ASP .Net 0 07-11-2003 04:13 AM
Project could not be opened because a language-specific compiler could not be instantieted Roxanne ASP .Net 0 07-04-2003 10:22 AM



Advertisments