Prev: Namespace vs. isnan
Next: strcpy_s vs strcpy
From: mpho on 16 Apr 2008 06:43 Hi all, This seems straightforward but gives this runtime error: terminate called after throwing an instance of 'std::bad_alloc' , what() : std9bad_alloc . I have: class X { int sz; T *ptr; public: X(int s, T *p) : sz(s), ptr(new T[s]) { assert(ptr != NULL); for (int i = 0, i < sz; i++) ptr[i] = p[i]; } //other members ~X() { delete ptr; ptr = NULL; } }; class Y { X xobj public: Y(int s, T *p) : xobj(s, p) { } //OK? //other members ~Y() { } //OK? }; then int main(){ ar[10] = {ten values}; Y yobj(10, ar); //problem here(?) ....... ...... } What's the problem above? Thank you. -- [ See http://www.gotw.ca/resources/clcm.htm for info about ] [ comp.lang.c++.moderated. First time posters: Do this! ]
From: Michael Aaron Safyan on 16 Apr 2008 18:48 mpho wrote: > Hi all, > > This seems straightforward but gives this runtime error: terminate > called after throwing an instance of 'std::bad_alloc' , what() : > std9bad_alloc . I have: [snip] > X(int s, T *p) : sz(s), ptr(new T[s]) [snip] > > ~X() { delete ptr; ptr = NULL; } [snip] > > What's the problem above? > Thank you. > You have called "delete" on an array allocated with "new[]". Memory allocated with "new[]" must be paired with "delete[]", not "delete". -- [ See http://www.gotw.ca/resources/clcm.htm for info about ] [ comp.lang.c++.moderated. First time posters: Do this! ]
From: Geert-Jan Giezeman on 16 Apr 2008 18:58 mpho wrote: > Hi all, > > This seems straightforward but gives this runtime error: terminate > called after throwing an instance of 'std::bad_alloc' , what() : > std9bad_alloc . I have: There are several errors in your code which make that it does not compile. There is also another error: you use array new in the constructor, but do not use array delete in the destructor. Below is a corrected version of your code. No runtime error occurs when I run it. That said, I would use std::vector or tr1::array, rather than making something like this myself. #include <cassert> // added typedef double T; // added class X { int sz; T *ptr; // added copy constructor and assignment operator, because // default ones don't make sense. X(X const &); X& operator=(X const &); public: X(int s, T *p) : sz(s), ptr(new T[s]) { assert(ptr != 0); // for (int i = 0, i < sz; i++) for (int i = 0; i < sz; i++) // comma should be semicolon ptr[i] = p[i]; } //~X() { delete ptr; ptr = 0; } ~X() { delete [] ptr; ptr = 0; } // array delete needed }; class Y { X xobj; // semicolon added public: Y(int s, T *p) : xobj(s, p) { } ~Y() { } }; int main(){ T ar[10] = {0.3}; Y yobj(10, ar); } -- [ See http://www.gotw.ca/resources/clcm.htm for info about ] [ comp.lang.c++.moderated. First time posters: Do this! ]
From: Antoon on 16 Apr 2008 18:57 "mpho" <tjabane(a)gmail.com> schreef in bericht news:bba322e0-ab00-491b-b15e-fc949b52115f(a)1g2000prg.googlegroups.com... > Hi all, > > This seems straightforward but gives this runtime error: terminate > called after throwing an instance of 'std::bad_alloc' , what() : > std9bad_alloc . I have: > > class X { > int sz; sz can be negative: it's better to use size_t instead. > T *ptr; > > public: > X(int s, T *p) : sz(s), ptr(new T[s]) > { > assert(ptr != NULL); > for (int i = 0, i < sz; i++) > ptr[i] = p[i]; > } > > //other members > > ~X() { delete ptr; ptr = NULL; } ^^^^^^^ This should be delete [] ptr; > }; > > class Y { > X xobj ^ Missing ; > > public: > Y(int s, T *p) : xobj(s, p) { } //OK? > //other members > ~Y() { } //OK? > }; > > then > > int main(){ > > ar[10] = {ten values}; > Y yobj(10, ar); //problem here(?) > ...... > ..... > } > > What's the problem above? > Thank you. > Antoon -- [ See http://www.gotw.ca/resources/clcm.htm for info about ] [ comp.lang.c++.moderated. First time posters: Do this! ]
From: acehreli on 16 Apr 2008 18:52
The following is not the code that's giving you trouble. It can't be compiled. I tried compiling your code for five minutes, then gave up. On Apr 16, 2:43 pm, mpho <tjab...(a)gmail.com> wrote: > This seems straightforward but gives this runtime error: terminate > called after throwing an instance of 'std::bad_alloc' , what() : > std9bad_alloc . std::bad_alloc is thrown when new cannot allocate the requested amount of memory. > I have: > > class X { > int sz; > T *ptr; > > public: > X(int s, T *p) : sz(s), ptr(new T[s]) > { > assert(ptr != NULL); That assertion will always succeed, because new never returns NULL, unless you explicitly request that behavior with 'nothrow' version of new: ptr(new (std::nothrow) T[s]) > for (int i = 0, i < sz; i++) Replace that comma with a semicolon. > ptr[i] = p[i]; > } > > //other members > > ~X() { delete ptr; ptr = NULL; } That's undefined behavior: you must use delete[] when you use new[]. Additionally, setting ptr to NULL is completely unnecessary, right? The object is about to die. Who will ever reference ptr? Surely, you did not give out the address of or a reference to it to your callers... > }; > > class Y { > X xobj A semicolon missing. > > public: > Y(int s, T *p) : xobj(s, p) { } //OK? That's OK. > //other members > ~Y() { } //OK? That's OK too. > }; > > then > > int main(){ > > ar[10] = {ten values}; > Y yobj(10, ar); //problem here(?) No, there is no problem there. The problem is in the code that you did not show, including the definition of T. Lastly, I recommend that you become familiar with the standard containers like std::vector. You will notice that your resource ownership headaches will vanish. :) Ali -- [ See http://www.gotw.ca/resources/clcm.htm for info about ] [ comp.lang.c++.moderated. First time posters: Do this! ] |