删除指向指针的指针会导致内存泄漏吗?

Will delete the pointer to pointer cause the memory leak?

我有一个关于 C 风格字符串符号常量和动态分配数组的问题。

const char** name = new const char* { "Alan" };
delete name;

当我在 new 一段内存后尝试 delete name 时,编译器建议我使用 delete 而不是 delete[]。我理解 name 仅存储指向唯一读取字符串的指针的地址。

但是,如果我只delete指向指针的指针(即name),字符串本身会不会导致内存泄漏?

正如上面的评论所指出的,您不需要管理“Alan”所在的内存。 让我们看看实际情况如何。

我修改了你的代码:

#include <iostream>

void test() {
    const char** name;
    name = new const char* { "Alan\n" };   
    delete name;
}

int main()
{
    test();
}

然后我将它弹出到 godbolt 中,它显示了引擎盖下发生的事情。 (摘录如下)

无论是clang还是gcc,存放“Alan\n”的内存都是静态内存,所以一直存在。这就是它不会造成内存泄漏的原因,即使您在提及它之后再也没有接触过它。 “Alan\n”指针的值只是程序内存中的位置,offset .L.strOFFSET FLAT:.LC0.

clang:

test():                               # @test()
        push    rbp
        mov     rbp, rsp
        sub     rsp, 16
        mov     edi, 8
        call    operator new(unsigned long)
        mov     rcx, rax
        movabs  rdx, offset .L.str
        mov     qword ptr [rax], rdx
        mov     qword ptr [rbp - 8], rcx
        mov     rax, qword ptr [rbp - 8]
        cmp     rax, 0
        mov     qword ptr [rbp - 16], rax       # 8-byte Spill
        je      .LBB1_2
        mov     rax, qword ptr [rbp - 16]       # 8-byte Reload
        mov     rdi, rax
        call    operator delete(void*)
.L.str:
        .asciz  "Alan\n"

gcc:

.LC0:
        .string "Alan\n"
test():
        push    rbp
        mov     rbp, rsp
        sub     rsp, 16
        mov     edi, 8
        call    operator new(unsigned long)
        mov     QWORD PTR [rax], OFFSET FLAT:.LC0
        mov     QWORD PTR [rbp-8], rax
        mov     rax, QWORD PTR [rbp-8]
        test    rax, rax
        je      .L3
        mov     esi, 8
        mov     rdi, rax
        call    operator delete(void*, unsigned long)