C 使用释放的内存真的会崩溃吗?

C 使用释放的内存真的会崩溃吗?,c,memory,memory-management,C,Memory,Memory Management,下面的代码将访问不再分配的内存 #include <stdio.h> int main() { int * ptr = new int(5); delete ptr; return *ptr; } #包括 int main() { int*ptr=新的int(5); 删除ptr; 返回*ptr; } 指针访问不再分配的内存,但在访问内存之前,它只返回一个值。 我想知道,实际上,程序是否可能以分段冲突信号结束崩溃 编辑:我在循环中运行

下面的代码将访问不再分配的内存

#include <stdio.h>
int main()
{
        int * ptr = new int(5);
        delete ptr;
        return *ptr;
}
#包括
int main()
{
int*ptr=新的int(5);
删除ptr;
返回*ptr;
}
指针访问不再分配的内存,但在访问内存之前,它只返回一个值。 我想知道,实际上,程序是否可能以分段冲突信号结束崩溃

编辑:我在循环中运行程序超过100000次而没有崩溃,这并不意味着它永远不会崩溃,只是它在这100000次中没有崩溃。也许用这么简单的程序是不可能的

我想知道这是否有可能导致程序崩溃,出现分段冲突信号或诸如此类的情况

对。取消引用已删除的指针是未定义的行为。可能发生的事情之一是撞车。另一个原因是程序可以无提示地退出,而不会出现任何问题

我想知道这是否有可能导致程序崩溃,出现分段冲突信号或诸如此类的情况


对。取消引用已删除的指针是未定义的行为。可能发生的事情之一是撞车。另一个原因是程序可以无提示地退出,而不会出现任何问题。

是的,您应该永远不要使用已释放的内存

在释放或删除堆分配内存后使用它会导致未定义的系统行为


有时它可以工作,有时它不工作,这取决于释放的内存是否被重用。

是的,您应该永远不要使用释放的内存

在释放或删除堆分配内存后使用它会导致未定义的系统行为


有时它可以工作,有时不工作,这取决于释放的内存是否被重用。

ptr仍然包含内存地址。是否在进程的上下文中访问此特定地址取决于操作系统的内存管理状态,以及系统的C++编译器的堆管理是否会返回由于删除到OS内存管理而释放的内存。如果它消失了,您将看到段冲突

但是,访问该地址仍然是可能的,并且您的程序不会因为非法侵入而终止。但是,即使这是肯定的,您也不能保证从main返回的值仍然是删除之前保存的变量值。堆内存管理是一个非常复杂的软件,在返回内存块时,无法知道内存块会发生什么变化

最后,如果您的程序使用线程,那么另一个线程可能已经请求了内存,并在几纳秒前接收并更改了返回的内容


所以:不要,永远,永远

ptr仍然包含一个内存地址。是否在进程的上下文中访问此特定地址取决于操作系统的内存管理状态,以及系统的C++编译器的堆管理是否会返回由于删除到OS内存管理而释放的内存。如果它消失了,您将看到段冲突

但是,访问该地址仍然是可能的,并且您的程序不会因为非法侵入而终止。但是,即使这是肯定的,您也不能保证从main返回的值仍然是删除之前保存的变量值。堆内存管理是一个非常复杂的软件,在返回内存块时,无法知道内存块会发生什么变化

最后,如果您的程序使用线程,那么另一个线程可能已经请求了内存,并在几纳秒前接收并更改了返回的内容

所以:不要,永远,永远

是的,它可能真的会崩溃;) 不过,您的示例实际上太简单,无法崩溃。为了使示例崩溃,您的进程(标准C库)必须在
delete
命令中将内存返回到操作系统。由于目前大多数系统的内存都很有限,因此必须分配足够大的内存,以便在释放内存时,整个页面都会被释放并返回到操作系统。当您访问未映射的内存时,会发生分段错误-返回到操作系统的内存就是这种情况。但是,您分配的内存太少,无法实现这一点

如果您想要崩溃,请给系统更多的机会:)

#包括
#包括
//您将分配的兆字节数
#定义N 100
int main()
{
字符*ptr[N];
int i;
对于(i=0;i
我的系统每次都会崩溃。即使在您的情况下,如果您的
int
仅仅是该页面上的最后一个内容(当然不确定,这取决于标准C库的实现),它也可能会崩溃,但这需要很多机会,并且取决于实现

我刚刚创建了一个更有可能发生崩溃的案例,让您相信它可能会发生:-)

是的,它可能真的会崩溃;) 不过,您的示例实际上太简单,无法崩溃。为了使示例崩溃,您的进程(标准C库)必须在
delete
命令中将内存返回到操作系统。由于目前大多数系统的内存都很有限,因此必须分配足够大的内存,以便在释放内存时,整个页面都会被释放并返回到操作系统。当您访问未映射的内存时,会发生分段错误-返回到操作系统的内存就是这种情况。但是,您分配的内存太少,无法实现这一点

如果你想要一个
#include <stdio.h>
#include <string.h>

// number of megabytes you will allocate
#define N 100
 
int main()
{
        char *ptr[N];
        int i;

        for (i = 0; i < N; i++) {
                ptr[i] = new char[1*1024*1024];
        }
        // if you remove the following loop, it won't crash
        for (i = 0; i < N; i++) {
                delete ptr[i];
        }
        return ptr[0][2000];
}
#include <stdio.h>
#include <string.h>

int main()
{
        size_t size = 1024*1024;
        char *ptr = new char[size];
        memset(ptr,255,size);
        delete [] ptr;
        return ptr[0];
}