0

Currently I'm writing a little bit of code to practice what I've been studying in a tutorial online. In this code, i allocated some space using 'new' using a pointer to create class instances, and iterate through them to set their names. However, I can only delete them when the pointer is at the 0th position. Can someone explain if I'm thinking of this incorrectly or what the general rule for this is?

//HEADER FILE

#include <iostream>
using namespace std;

class Animal {
private:
    string name;
    int age;

public:
    Animal(string name = "UNDEFINED", int age = 0): name(name), age(age) {cout << "Animal created" << endl;}
    ~Animal() {cout << "Animal killed" << endl;}
    void setName(char name) {this->name = name;}
    void speak() {cout << "My name is: " << name << ", and my age is: " << age << endl;}

};

//MAIN FILE

#include "Animal.h"

int main() {
    char name = 'a';

    Animal *animals = new Animal[10];
    for (int i = 0; i < 10; i++, animals++, name++) {
        animals->setName(name);
        animals->speak();
    }
    animals -= 10;
    delete[] animals;

    return 0;
}

The deconstructor is only called when the line 'animals -= 10' is included, but not when it is omitted or when 10 is any other number.

Arne
  • 1,293
  • 1
  • 7
  • 20
mattloulou
  • 37
  • 5
  • When an array of objects is allocated by new, hidden info including the size of the array is saved, usually just before the pointer. So it's necessary for the pointer to point to the first object in the array to access that info. And the Standard requires it as the answers below describe. – doug Jul 22 '19 at 04:20

1 Answers1

5

does a pointer need to be pointing at the first object in an allocated class array to use 'delete [] ptrName'?

Yes.

The standard says (quoting the draft):

[expr.new]

When the allocated object is an array (that is, the noptr-new-declarator syntax is used or the new-type-id or type-id denotes an array type), the new-expression yields a pointer to the initial element (if any) of the array. ...

[expr.delete]

... In an array delete expression, the value of the operand of delete may be a null pointer value or a pointer value that resulted from a previous array new-expression. If not, the behavior is undefined. ...

Since the result of new[] is the address of the initial element, the address of any other sibling element is not a result of a new[], and thus applying delete[] on a pointer to any other element results in undefined behaviour.

Community
  • 1
  • 1
eerorika
  • 232,697
  • 12
  • 197
  • 326
  • 2
    @Chipster The sections have numbers too, but it's better to not cite them, as they change between different versions of the standard. Same goes for numbers of the rules themselves – eerorika Jul 22 '19 at 02:55
  • Always cite the section name `[expr.new]` optionally site the number section if you know what version number of the standard you have `n4820 7.6.2.7 New [expr.new] Paragraph 6` as sometimes the sections are big and you may want to cite a specific paragraph. They are easy to retrieve: https://stackoverflow.com/a/4653479/14065 – Martin York Jul 22 '19 at 08:28