User 13204940 Ответов: 2

Ключевое слово C++ 'new' и управление памятью не обязательно с помощью 'new'


Привет,

Просто быстрый вопрос об управлении памятью, скажем, у меня есть следующее:

const std::vector<int> intArray = {1, 2, 3};
delete intArray;
Это должно выделить память для массива, а затем снова освободить ее.

Как это работает в данной ситуации?
doSomething({1, 2, 3});

void doSomething(const std::vector<int> arr)
{
        // whatever
}
Здесь нет никакой возможности удалить исходный массив. Что из нижеследующего я должен сделать?

1. ничего, что память уже будет управляться.

2.
const std::vector<int> arr = {1, 2, 3};
doSomething(arr);
delete arr;

void doSomething(const std::vector<int> arr)
{
        // whatever
}

3.
const std::vector<int>* arr = {1, 2, 3};
doSomething(arr);

void doSomething(const std::vector<int>& arr)
{
        delete arr;
}


Я также не уверен, что синтаксис для 1 и 2 верен, пожалуйста, сообщите мне о любых проблемах, которые вы там видите.

Что я уже пробовал:

------------------------------------------------------------------------------

2 Ответов

Рейтинг:
2

Jochen Arndt

Если вы объявляете объект в стеке, как в вашем случае, он автоматически уничтожается при выходе из области видимости.

Как уже отмечалось в вашем другом вопросе, вы должны передать его по ссылке, чтобы избежать создания копии.

Так и должно быть:

{
    const std::vector<int> arr = {1, 2, 3};
    doSomething(arr);

    // arr goes out of scope here at the end of the block
    // The desctructor is called and any memory is freed
}

void doSomething(const std::vector<int>& arr)
{
    // do something
}

Если вы передадите массив по значению:
// A temporary copy of the passed array is created and assigned to arr
void doSomething(const std::vector<int> arr)
{
    // do something

    // The destructor of arr is called here when returning from the function
    // The original array passed from the caller still exists
}


Рейтинг:
1

Leo Chapiro

Вы пробовали скомпилировать этот код:

const std::vector<int> intArray = {1, 2, 3};
delete intArray;


Я думаю, что нет, потому что вы должны получить ошибку на "delete intArray", например "выражение должно быть указателем".

Вы можете удалить только объекты, созданные в куче с помощью "new", а не такие объекты стека, как intArray: взгляните на оператор delete.


[no name]

Ах да, вот тут-то все и отличается от других языков, к которым я привык, что-то вроде

Object obj;
в другом языке вы бы создали объект, но не сконструировали его, и вам пришлось бы иметь
obj = new Object();
впоследствии. Из того, что я понимаю, просто что-то вроде
Object obj;
в C++ все это уже делается.

Таким образом, это создает переменную в стеке, в то время как
Object obj = new Object();
создаст переменную в куче и поэтому потребует
delete obj;


Когда вы используете 'new' без аргументов, обязательно ли вам иметь () после типа объекта или вы можете оставить его без него, как это?

Object obj = new Object;

Rick York

Следует иметь в виду, что в C++ оператор new создает объект и возвращает на него указатель. Ваше заявление должно быть:

Object * pobj = new Object;
Скобки нужны только в том случае, если вы передаете параметры конструктору объекта, например:
Object * pobj = new Object( param1, param2 );