Это вызывает утечку памяти? - PullRequest
       21

Это вызывает утечку памяти?

4 голосов
/ 06 сентября 2010
void aFunction_2()
{
    char* c = new char[10];
    c = "abcefgh";
}

Вопросы:

  1. Будет ли: c = "abdefgh" сохранено в new char[10]?

  2. Если c = "abcdefgh" - это еще одна область памяти, я должен освободить ее?

  3. Если бы я хотел сохранить информацию в char[10], я бы использовал функцию типа strcpy, чтобы поместить информацию в char[10]?

Ответы [ 5 ]

8 голосов
/ 06 сентября 2010

Да, это утечка памяти.

Да, вы бы использовали strcpy для помещения строки в выделенный массив символов.

Так как это код на C ++, вы не сделали бы ни того, ни другого. Вы бы использовали std :: string.

6 голосов
/ 06 сентября 2010
void aFunction_2()
{
    char* c = new char[10]; //OK
    c = "abcefgh";          //Error, use strcpy or preferably use std::string
}

1- Будет ли выделено: c = "abdefgh" внутри нового символа [10]?

нет, вы меняете указатель с ранее указывающего наячейка памяти размером 10 байтов, указывающая на новую константную строку, вызывающую утечку памяти в десять байтов.

2- Если c = "abcdefgh" - это еще одна область памяти, следует ли ее освободить?

нет, он не был выделен в куче, он находится в постоянной памяти

3 - Если бы я хотел сохранить информацию внутри символа [10], я бы использовалфункция, подобная strcpy, для помещения информации в символ [10]?

не уверен, что вы подразумеваете под словом «внутренний».когда вы выделяете с помощью new, память выделяется в куче, и в обычных условиях доступ к ней возможен из любой части вашей программы, если вы указали указатель на блок памяти.

0 голосов
/ 06 сентября 2010
  1. Нет, это только переназначение указателя;
  2. Нет, delete что-то, что не пришло из new, часто вылетает; и
  3. Да, strcpy выполнит работу ... но обычно это не используется в C ++.

Поскольку никто не ответил с кодом, std::uninitialized_copy_n (или просто std::copy_n, здесь на самом деле это не имеет значения) больше C ++, чем strcpy:

#include <memory>

static char const abcs[] = "abcdefgh"; // define string (static in local scope)
char *c = new char[10]; // allocate
std::copy_n( abcs, sizeof abcs, c ); // initialize (no need for strlen)

// when you're done with c:
delete[] c; // don't forget []

Конечно, std::string - это то, что вы должны использовать вместо:

#include <string>
std::string c( "abcdefgh" ); // does allocate and copy for you
// no need for delete when finished, that is automatic too!
0 голосов
/ 06 сентября 2010

На ваш ответ уже отвечали несколько раз, но я думаю, что во всех ответах отсутствует один важный бит (который вы не просили явно): хотя вы выделили память для десяти символов, а затем перезаписали единственный указатель, на который вы ссылаетесь в этой областипамяти, вы создали утечку памяти, которую вы больше не можете исправить.Чтобы сделать это правильно, вы должны std :: strcpy () память из предварительно выделенной, предварительно инициализированной константной части памяти, где содержимое вашего строкового литерала было сохранено в 10 динамически распределенных символах.

А вот и важная часть:

Когда вы закончите работу с этими 10 символами, вы освободите их, используя delete[].[] важны здесь.Все, что вы выделяете с помощью new x[], должно быть освобождено с delete[].Ни компилятор, ни среда выполнения не предупреждают вас при использовании обычного delete, поэтому важно запомнить это правило.

0 голосов
/ 06 сентября 2010
  1. Нет (переназначение указателя)
  2. Нет
  3. Да, вы можете использовать strcpy(), см. , например :
...