Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

deleting a pointer or array of pointers

49 views
Skip to first unread message

goodm...@gmail.com

unread,
Jan 26, 2017, 2:14:41 AM1/26/17
to


class MyClass
{
public:
MyClass(int questionsCount)
{
this->questionsCount = questionsCount;
answers = new int[questionsCount]; // allocating space
for (int i = 0; i < questionsCount; i++)
{
answers[i] = -1;
}
}
~MultipleChoiceTest()
{
delete [] answers; // <------- (1)
delete answers; (2)
}

protected:
int questionsCount;

private:
int* answers;
};


In the class above in the destructor I am not sure if (1) has to be used or (2) ..... My best guess would be (2) as i only have one pointer not an array of pointers ... Am I right ??

Öö Tiib

unread,
Jan 26, 2017, 3:46:03 AM1/26/17
to
You can't have destructor ~MultipleChoiceTest() in class
MyClass. Idea for the future: paste compiling code to your posts.
Otherwise your defects distract and confuse the audience.

You used new[] to allocate 'answers' so you should use delete[]
to deallocate those as well. However in general it is not advisable
to use raw pointer for dynamic size array in C++ since we have
std::vector that already does what we usually need to do with
dynamic sized array and it does that more safely:

#include <vector>

class MyClass
{
public:
// define types we use so if we need to change those
// later then less changes needed
using Ints = std::vector<int>;
using Count = Ints::size_type;

// use explicit here to avoid various ints silently
// converting into Myclass
explicit MyClass(Count questionsCount)
: answers(questionsCount, -1)
{}

protected:
Count questionsCount() {return answers.size();}

private:
Ints answers;
};

int main()
{
MyClass plorp(15);
}


Compiler-generated default destructor, copy constructor/assignment
and move constructor/assignment are all fine for MyClass like above.
In your implementation these were defective.

Richard

unread,
Jan 26, 2017, 4:17:48 PM1/26/17
to
[Please do not mail me a copy of your followup]

goodm...@gmail.com spake the secret code
<c381631c-9f6a-4ecd...@googlegroups.com> thusly:

>class MyClass
>{
>public:
> MyClass(int questionsCount)
> {
>[...]
> answers = new int[questionsCount]; // allocating space
>[...]
> }
> ~MultipleChoiceTest()
> {
> delete [] answers; // <------- (1)
> delete answers; (2)
> }
>[...]
>};
>
>In the class above in the destructor I am not sure if (1) has to be
>used or (2) ..... My best guess would be (2) as i only have one
>pointer not an array of pointers ... Am I right ??

Match scalar delete with scalar new:

int *one = new int;
delete one;

Match array delete with array new:

int *bunches = new int[10];
delete[] bunches

There are source code analysis tools that will catch mismatched
array/scalar new/delete.

From this code, it looks like you are just learning the language.
From this perspective you need to understand the low-level new and
delete operators and how they are used.

From a practical day-to-day perspective, you don't really need to
handle raw pointers much. Instead you use an appropriate "resource
container" for dynamically allocated memory. Need a dynamically
resizable array? Use std::vector. Need an object allocated on the
heap? Use std::unique_ptr or std::shared_ptr for unique or shared
ownership of the allocated object. Resource container classes manage
the raw pointers for you, so you don't need to worry about how you
should call new or how you should call delete.
--
"The Direct3D Graphics Pipeline" free book <http://tinyurl.com/d3d-pipeline>
The Terminals Wiki <http://terminals-wiki.org>
The Computer Graphics Museum <http://computergraphicsmuseum.org>
Legalize Adulthood! (my blog) <http://legalizeadulthood.wordpress.com>

Juha Nieminen

unread,
Jan 31, 2017, 10:30:52 AM1/31/17
to
goodm...@gmail.com wrote:
> class MyClass
> {
> public:
> MyClass(int questionsCount)
> {
> this->questionsCount = questionsCount;
> answers = new int[questionsCount]; // allocating space
> for (int i = 0; i < questionsCount; i++)
> {
> answers[i] = -1;
> }
> }
> ~MultipleChoiceTest()
> {
> delete [] answers; // <------- (1)
> delete answers; (2)
> }

This demonstrates why you should really avoid doing your own allocations,
if you can, and instead use the standard containers, if they suffice for
the task. std::vector does not only make your class much simpler to
implement, but also safer.

If you really, really need to do your own allocation, because the
standard containers just don't do what you need, then you have to
either disable or implement the copy constructor and assignment
operator of that class. Else you have a big problem leading to
multiple deallocations and accessing deallocated memory.

Disabling the copy constructor and assignment operator is the
easiest solution. But if you class really, really needs them enabled,
then it becomes quite a laborious task to implement them.
0 new messages