Thread Rating:
  • 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5
C++ string help
#1
Say I have a class:

header file:
Code:
class Widget {
   public:
    Widget(string);
    ~Widget();
  private:
    string name;
};

definition file:

Code:
Widget::Widget(string name) {
  // 1
}

Widget::~Widget() {
  // 2
}

At position 1, I want to assign to the private "name" field the value passed in, which is a string.

Currently I am doing it by:

Code:
this->name = name

Is this correct? Will it result in memory leaks?

And at position 2, I can't seem to get the memory for it freed correctly. If I do:

Code:
delete [] name;

It complains that I didn't pass a pointer to delete. Any other way I try I get a segfault...

So what should be done in the destructor?
Reply
#2
Copying the string that way is OK.

I don't think you need to delete strings. I'm pretty sure the destructor is called once it goes out of scope (you have MUCH MORE than 640k RAM so it doesn't matter if it lingers until the program ends). You only have to manually delete strings if you use char* instead of the string class.

EDIT: to clear strings (I think it happens automatically), use
str.erase(0, str.length());

Some info:
http://www.cprogramming.com/tutorial/string.html
Reply
#3
Your private member string is being allocated on the stack - not on the heap - therefore you do not need to delete it when you're finished. Also, in your constructor, you should pass the argument by reference, not by value. i.e.

Code:
Widget::Widget(string& name)
{
    this->name = name; // this is legal since the assignment operator in std::string is overloaded.
}

You would only need to worry about freeing the memory if you created the private string using 'new'. e.g.

Code:
using namespace std;

class Widget
{
    private:
        string* name;

    public:
        Widget(string& name);
        virtual ~Widget();
};

Code:
Widget::Widget(string& name)
{
    this->name = new string(name); // using the copy-constructor
}

Widget::~Widget()
{
    delete name;
}

The 'delete[]' operator is only used to deallocate an array; not a single object. For example:

Code:
char* myString = new char[512];

// ...

delete[] myString;

Code:
string* myString = new string(); // a single object

// ...

delete myString;
img]http://www.cdsoft.co.uk/misc/shiftlynx.png[/img]
Reply
#4
Quote:Your private member string is being allocated on the stack - not on the heap - therefore you do not need to delete it when you're finished. Also, in your constructor, you should pass the argument by reference, not by value. i.e.

Code:
Widget::Widget(string& name)
{
    this->name = name; // this is legal since the assignment operator in std::string is overloaded.
}

Unfortunately I have little control over the method signature - I'm doing a lab for my course Wink

They have given the signature to me like that. Nor is the string a pointer to string, so I guess this->name is all correct.

Quote:You would only need to worry about freeing the memory if you created the private string using 'new'. e.g.

Code:
using namespace std;

class Widget
{
    private:
        string* name;

    public:
        Widget(string& name);
        virtual ~Widget();
};

Code:
Widget::Widget(string& name)
{
    this->name = new string(name); // using the copy-constructor
}

Widget::~Widget()
{
    delete name;
}

Oh, I get it now!

Yesterday, I was trying to assign the string with this->name = new string(name). But it wouldn't work, the compiler threw an error. But that's because the .h file says that name is a string, not pointer to string.

And of course, it should be delete when I change it and not delete [], because string is an object, not an array.

It all makes so much more sense once it's explained...

Of course, really the constructor should take const & string instead of string, right?

Quote:EDIT: to clear strings (I think it happens automatically), use
str.erase(0, str.length());

I might put that in the destructor, because if shiftLynx is correct there really isn't any need for the destructor otherwise...
Reply
#5
do you want the string on the stack or the heap?

In your original code:

Code:
class Widget {
   public:
    Widget(string);
    ~Widget();
   private:
    string name;
};

since Widget::name is not a pointer, it is on the stack. C++'s std::string class will automatically do whatever memory allocation / resizing is necessary for name.

You never delete an object that was not created with new, so your original question as to why delete wasn't working is because you never used new.

if however, your string name was declared as a pointer (i.e., string *name), then you'd have to use new, and indeed, you would have a memory leak if your deconstructor never deleted the string.

-neuro
ignatures suck
Reply


Forum Jump:


Users browsing this thread: 1 Guest(s)