首页
学习
活动
专区
工具
TVP
发布
精选内容/技术社群/优惠产品,尽在小程序
立即前往

在释放它们之后真的应该将指针设置为"NULL"吗?

在释放指针之后,将指针设置为"NULL"是一种很好的做法。这样可以避免在释放内存后继续使用指针,从而导致未定义的行为。当指针被释放后,它所指向的内存块将被释放,因此不应再被访问。将指针设置为"NULL"可以确保在尝试访问已释放内存时,程序将立即报错,而不是继续执行错误的代码。

例如,假设我们有以下代码:

代码语言:c++
复制
int* p = new int(10);
delete p;

在释放内存之后,我们可以将指针设置为"NULL":

代码语言:c++
复制
int* p = new int(10);
delete p;
p = NULL;

这样,如果在后续代码中尝试访问指针"p",程序将立即报错,而不是继续执行错误的代码。

页面内容是否对你有帮助?
有帮助
没帮助

相关·内容

C++内存管理(建议收藏)

(2)函数的return语句写错了,注意不要返回指向“栈内存”的“指针”或者“引用”,因为该内存在函数体结束时被自动销毁。 (3)使用free或delete释放了内存后,没有指针设置NULL。...导致产生“野指针”。 【规则1】用malloc或new申请内存之后应该立即检查指针值是否NULL。防止使用指针NULL的内存。 【规则2】不要忘记为数组和动态内存赋初值。...【规则5】用free或delete释放了内存之后,立即将指针设置NULL,防止产生“野指针”。...所以,指针变量创建的同时应当被初始化,要么指针设置NULL,要么让它指向合法的内存。...所以,我打算只将析构函数设置private。再进一步,析构函数设为private除了会限制栈对象生成外,还有其它影响?是的,这还会限制继承。

3.1K41

【C进阶】——动态内存管理详解 及 经典笔试题解析

使用后: 我们初始化之后,里面放的就是0到9了。 如果参数size_t size0,则返回值取决于特定的库实现(它可能是也可能不是空指针),但返回的指针不应被解引用。...那释放之后,是不是就万事大吉了呢? 不,我们还应该做一件事情: 把p置空 p = NULL; 为什么要这样做呢? 大家想一下,我们现在虽然已经把p指向的那块空间给释放掉了。...为了避免这种情况发生: 我们释放掉p指向的空间之后,要及时p置空。...因为如果free的参数 ptr 接收的是NULL指针,不执行任何操作。 所以: 使用free释放一块动态内存空间后,及时指向起始位置的指针置空是一个好习惯。...3.6 动态开辟内存忘记释放(内存泄漏) 就是我们动态开辟的空间使用完之后,一定要记得释放,不释放的话有可能会造成内存泄漏。 切记: 动态开辟的空间一定要释放,并且正确释放

15910
  • 从源码角度彻底理解ReentrantLock(重入锁)

    /构造新结点,CAS方式设置队列首元素,当head==null时更新成功 tail = head;//尾指针指向首结点 } else { //队列不为空...其中只有更新头指针和更新尾指针这两步进行了CAS同步,可以预见高并发场景下性能是非常好的。但是本着质疑精神我们不禁会思考下这么做真的线程安全?...,所以6何时执行对线程安全不会有任何影响,比如下面这种情况 为了确保真的理解了它,可以思考这个问题:把enq方法图中的4放到5之后,整个入队的过程还线程安全?...第一个if分句中,当前线程首先会判断前驱结点是否是头结点,如果是则尝试获取锁,获取锁成功则会设置当前结点头结点(更新头指针)。为什么必须前驱结点头结点才尝试去获取锁?...从这个意义上,对于同步队列中等待的线程而言,它们获得锁的顺序和加入同步队列的顺序一致,这显然是一种公平模式。

    55240

    手把手教玩你转动态内存管理(InsCode Stable Diffusion 美图活动一期)

    因此,使用malloc的时候我们应该秉承着用完就释放的原则 这样不仅能大大提高计算机的工作效率,还能增加内存空间的利用率。...a = NULL; //此时a是野指针,因此a重新变为空指针,避免后面再使用的时候出现问题 } 开辟成功: ​ 开辟失败: ​ 2.calloc 2.1认识calloc ​ calloc函数的返回类型指针...从这里看,它与malloc的作用几乎是一模一样,只是多了一步内容初始化为0,不过讲真的,即使calloc不比malloc多这一步,我也更愿意使用calloc而不是malloc,因为calloc函数的两个参数可以让你很好的知道你当时开辟这个空间的用途...);//释放开辟的空间 a = NULL;//a现在是野指针,将其变为空指针 } 3.realloc 3.1认识realloc ​ realloc函数的返回类型指针,因此我们接收它返回的地址时要用到强制类型转换...x的空间 x = NULL; //指针指针,避免在后面使用 } ​ 3.指针可以替代柔性数组的作用 #include #include struct

    13510

    MIT 6.S081 -- Virtual memory for applications

    看起来mprotect暗示了你可以为单独的地址添加不同的权限,然而在XV6中,我们只能为整个Page设置相同的权限,这里是有区别? 不,这里并没有区别,它们都在Page粒度工作。...举个例子,现在当根节点需要读出其指向的一个对象时,这个对象仍然from空间。这是危险的,因为我们不应该跟踪from空间的指针(注,换言之GC时的指针跟踪都应该同一个空间中完成)。...之后的过程与前面描述的相同,开始GC时,我们根节点对象拷贝到to空间,但是根节点中的指针还是指向了位于from空间的对象。...所以现在我们to空间中,有N个对象位于一个Page中,并且它们都没有被扫描。之后某个时间,Page Fault Handler会被调用,GC会遍历这个内存Page上的N个对象,并检查它们指针。...有一个问题,你应该在这里使用虚拟内存?或者说这里的这些技巧值得?许多的GC并没有使用虚拟内存,而是通过编译器生成的代码来完成GC,并且还有各种其他的技巧来减少性能损耗。

    30930

    C++后台实习面经 - 腾讯WXG

    僵尸进程 Q:介绍一下僵尸进程吧 A:僵尸进程就是死掉之后还没有被父进程wait的进程,它们在运行结束之后PCB这些资源还没有被释放,等待父进程wait它们获得它们的状态。......有两个信号,一个SIGCHLD、一个SIGCLD,设置这两个信号的处理方式忽略,它们告诉内核,不关心子进程结束的状态所以当子进程终止的时候直接释放所有资源就行。...右值引用的话,底层是原来的对象进行了一份内存拷贝,然后封装了对这个拷贝的指针。...LT为了担责,降低了效率,而ET为了效率责任推给了用户 最后的一分钟 Q:好了,面试就到这里了,你这两天还在** A:嗯还在,接下来会有什么安排 Q:我马上给你安排一下复面,你应该很快就能收到消息...A:评价一下我 Q:本科有这个基础已经够了,但是还是有一些不足 A:数据库和网络 Q:你的数据库基础不是很好 A:好的,谢谢,接下来还会有什么安排 Q:你回去等通知吧,我尽快让HR联系你,明天应该就行

    1.2K40

    C++后台腾讯WXG实习面经(已拿offer)

    僵尸进程 Q:介绍一下僵尸进程吧 A:僵尸进程就是死掉之后还没有被父进程wait的进程,它们在运行结束之后PCB这些资源还没有被释放,等待父进程wait它们获得它们的状态。......有两个信号,一个SIGCHLD、一个SIGCLD,设置这两个信号的处理方式忽略,它们告诉内核,不关心子进程结束的状态所以当子进程终止的时候直接释放所有资源就行。...右值引用的话,底层是原来的对象进行了一份内存拷贝,然后封装了对这个拷贝的指针。...LT为了担责,降低了效率,而ET为了效率责任推给了用户 最后的一分钟 Q:好了,面试就到这里了,你这两天还在** A:嗯还在,接下来会有什么安排 Q:我马上给你安排一下复面,你应该很快就能收到消息...A:评价一下我 Q:本科有这个基础已经够了,但是还是有一些不足 A:数据库和网络 Q:你的数据库基础不是很好 A:好的,谢谢,接下来还会有什么安排 Q:你回去等通知吧,我尽快让HR联系你,明天应该就行

    2.2K100

    C++后台腾讯WXG实习面经(已拿offer)

    僵尸进程 Q:介绍一下僵尸进程吧 A:僵尸进程就是死掉之后还没有被父进程wait的进程,它们在运行结束之后PCB这些资源还没有被释放,等待父进程wait它们获得它们的状态。......有两个信号,一个SIGCHLD、一个SIGCLD,设置这两个信号的处理方式忽略,它们告诉内核,不关心子进程结束的状态所以当子进程终止的时候直接释放所有资源就行。...右值引用的话,底层是原来的对象进行了一份内存拷贝,然后封装了对这个拷贝的指针。...LT为了担责,降低了效率,而ET为了效率责任推给了用户 最后的一分钟 Q:好了,面试就到这里了,你这两天还在** A:嗯还在,接下来会有什么安排 Q:我马上给你安排一下复面,你应该很快就能收到消息...A:评价一下我 Q:本科有这个基础已经够了,但是还是有一些不足 A:数据库和网络 Q:你的数据库基础不是很好 A:好的,谢谢,接下来还会有什么安排 Q:你回去等通知吧,我尽快让HR联系你,明天应该就行

    73850

    动态内存管理

    5.对于ptr作用于free后,动态内存被释放,但ptr的值依然不会变(变为野指针),所以因为他变为了野指针,我们此时应该及时将其变为空指针NULLNULL被使用需要加头文件stdio.h) 还要额外说一些点...调整之后内存空间新⼤⼩(可以变大可以变小) 返回值调整之后的内存起始位置。...当空间开辟失败后,会返回NULL指针(没有能够开辟的空间) 当开辟成功后 如果你是要将其空间变大,分为两种: 原有空间之后没有足够大的空间(该空间后面也存在开辟空间,其中间隔不够大),就会在堆区中再去找一个合适大小的连续空间...(ptr, 1000);//这样可以?...(内存泄露) 之前讲free时就讲过内存泄露问题,使用完该动态内存之后一定要释放,否则会造成内存泄露问题。

    13210

    常见的C编程段错误及对策

    (a)); memset 函数有三个参数,第一个是要被设置的内存起始地址;第二个参数是要被设置的值;第三个参数是要被设置的内存大小,单位byte。...5、内存释放之后 既然使用free 函数之后指针变量p 本身保存的地址并没有改变,那我们就需要重新把p的值变为NULL: p = NULL; 这个NULL 就是我们前面所说的“栓野狗的链子”。...比如:free(p)之后,你用if(NULL != p)这样的校验语句还能起作用?...= p) { /* 没有起到防错作用*/ strcpy(p, “world”); /* 出错*/ } 释放完块内存之后,没有把指针NULL,这个指针就成为了“野指针”,也有书叫“悬垂指针”。...所以一定要记住一条:free 完之后,一定要给指针NULL。 同时留一个问题:对NULL 指针连续free 多次会出错?为什么?如果让你来设计free函数,你会怎么处理这个问题?

    1.5K41

    【python进阶】Garbage collection垃圾回收1

    实际上,它们负责三个重要任务: 新⽣成的对象分配内存 识别那些垃圾对象 从垃圾对象那回收内存 如果应⽤程序⽐作⼈的身体:所有你所写的那些优雅的代码,业务逻辑, 算法,应该就是⼤脑。...期初,Python这个值设置1: ? 值1说明分别有个⼀个指针指向或是引⽤这三个对象。假如我们现在创建⼀个新的Node实例,JKL: ? 与之前⼀样,Python设置JKL的引⽤数1。...之后Ruby轮询所有指针,变量 和代码产⽣别的引⽤对象和其他值。同时Ruby通过⾃身的虚拟机便利内部指针。标记出这些指针引⽤的每个对象。我图中使⽤M表示。 ?...现在,假定我们的程序不再使⽤这两个节点了,我们 n1 和 n2 都设置 null(Python中是None)。 ? 好了,Python会像往常⼀样每个节点的引⽤计数减少到1。...随着你的程序运⾏,Python解释器保 持对新创建的对象,以及因为引⽤计数零⽽被释放掉的对象的追踪。从理论上说,这两个值应该保持⼀致,因为程序新建的每个对象都应该最终被释放掉。 当然,事实并⾮如此。

    1K70

    (修订)斩获腾讯微信后台开发offer大神的近1.5W字的面试干货分享

    PCB这些资源还没有被释放,等待父进程wait它们获得它们的状态。...…有两个信号,一个SIGCHLD、一个SIGCLD,设置这两个信号的处理方式忽略,它们告诉内核,不关心子进程结束的状态所以当子进程终止的时候直接释放所有资源就行。...右值引用的话,底层是原来的对象进行了一份内存拷贝,然后封装了对这个拷贝的指针。...LT为了担责,降低了效率,而ET为了效率责任推给了用户 最后的一分钟 Q:好了,面试就到这里了,你这两天还在** A:嗯还在,接下来会有什么安排 Q:我马上给你安排一下复面,你应该很快就能收到消息...所以我猜想它们的实现里,一定是迭代器与容器进行了关联,每次对迭代器进行操作时候,都会根据容器检验迭代器的有效性,如果无效就抛出异常。

    1.8K40

    蒋豆芽面试题专栏总结(C++软件开发与嵌入式软件)完成了!

    ,或者是它所指向的内存空间已经被释放,所以实际使用的过程中,我们并不能通过指针判空去识别一个指针是否指针。...第二:分配的内存的指针以链表的形式自行管理,使用完毕之后从链表中删除,程序结束时可检查改链表。 第三:使用智能指针。...new发生错误抛出异常,malloc返回null 说说使用指针需要注意什么? 定义指针时,先初始化为NULL。 用malloc或new申请内存之后应该立即检查指针值是否NULL。...防止使用指针NULL的内存。 不要忘记为数组和动态内存赋初值。防止未被初始化的内存作为右值使用。...避免数字或指针的下标越界,特别要当心发生“多1”或者“少1”操作 动态内存的申请与释放必须配对,防止内存泄漏 用free或delete释放了内存之后,立即将指针设置NULL,防止“野指针” 初始化为0

    2K41

    C语言动态内存管理超详解

    ;//除了free掉空间,注意指针NULL,避免后续解引用野指针 return 0; } 运行结果: 如果我们把上面的calloc换成 malloc 会怎么样呢?...情况2 当是情况2的时候,原有空间之后没有足够多的空间时,扩展的方法是:堆空间上另找一个合适大小的连续空间来使用,原来空间的数据拷贝到新的空间,并将原来的空间释放。.../重复释放 } 当第一次释放之后,p就变成了野指针,那么再次进行释放,就和释放一个非动态开辟的指针一样了,会导致程序崩溃。...正确的做法是使用二级指针&str传过去。...掉str之后对str进行操作的,换言之,后面的操作都是在对一个野指针进行的,VS上,这个代码可以正常运行,但编译器会给出警告,我们应该避免写出这样不合规范的代码。

    14810

    动态内存管理基础详解

    每当free函数释放空间后,指针就没有被指向的内容,为了防止野指针,需要将其设为控制(即每次使用free函数后,都需要置成空指针) free函数不能释放非动态开辟的内存空间,这种行为是标准未定义的 如果...参数和返回值: ptr是要调整的内存地址,size是调整之后的新大小(以字节单位),返回值调整之后的内存起始位置。如果ptr指针,那么函数的功能与malloc函数一样。...(4)、返回新空间的起始地址 疑问:那realloc的返回值用原有的指针接受?...因此我们应该用一个新的指针去接受,然后判断增容是否成功,如果成功,就将新指针的内容赋给原有的指针,否则程序结束。...,而是后面相当于动态内存的一部分,此时再用free释放是不对的,free释放应该从动态内存的起始地址开始释放

    9110

    C语言进阶-动态内存管理柔性数组

    如果开辟失败,则返回一个NULL指针,因此malloc的返回值一定要做检查 返回值的类型是 void* ,所以malloc函数并不知道开辟空间的类型,具体使用的时候使用者自己来决定(需要用强制类型转化成所需要的指针类型...= ptr)//判断ptr指针是否空 { int i = 0; for(i=0; i<num; i++) { *(ptr+i) = 0; } } free(ptr);//释放ptr所指向的动态内存...(单位字节) 返回值调整之后的内存起始位置(同样需要更具需要进行强制类型转化来访问空间) realloc调大内存空间时存在两种情况: 情况1:原有空间之后有足够大的空间 要扩展内存就直接原有内存之后直接追加空间...原来空间的数据不发生变化 realloc()返回原指针 情况2:原有空间之后没有足够大的空间 堆空间上找到另一个空间(合适大小的连续空间,足够所要开辟空间的大小)来开辟 同时原来开辟空间所存有的内存进行拷贝...} 解释: char *GetMemory(void) { //字符数组栈上开辟 char p[] = "hello world"; //函数结束,对应开辟的空间会被还给电脑,此时p悬空指针

    64420

    C 语言内存泄露很严重,如何应对?

    一般的来讲,堆内存有如下两种获取方法: 方法一:函数返回值直接赋给指针,一般表现形式如下: char *local_pointer_xx = NULL; local_pointer_xx = (char...data) 方法二:指针地址作为函数返回参数,通过返回参数保存堆内存地址,一般表现形式如下: int ret; char *local_pointer_xx = NULL; /**转换后的字符串...内存释放误区 稍微使用过 C 语言编写代码的人,都应该知道堆内存申请之后是需要释放的。但为何还这么容易出现内存泄漏问题呢?...对于不熟悉的接口,要找到对应的接口文档或源代码分析;又或者看看代码中其它地方对该接口的引用,是否进行了内存释放; (3)如果确认对局部指针存在内存申请操作,就需要分析该内存的去向,是会被保存在全局变量...又或者会被作为函数返回值?如果都不是,就需要排查函数所有有”return“的地方,保证内存被正确释放

    48820

    动态内存管理学不懂,小代老师带你深入理解动态内存管理(上卷)

    • 如果参数 ptr 指向的空间不是动态开辟的,那free函数的⾏是未定义的。 • 如果参数 ptr 是NULL指针,则函数什么事都不做。...p = NULL;//释放后p还记得原来的地址很可怕的,把p赋值NULL return 0; } 3calloc和realloc 3.1calloc C语⾔还提供了⼀个函数叫 calloc ,...函数原型如下: void* realloc(void *ptr,size_t size) • ptr 是要调整的内存地址 • size 调整之后新⼤⼩ • 返回值调整之后的内存起始位置。...• realloc调整内存空间的是存在两种情况: ◦ 情况1:原有空间之后有⾜够⼤的空间 ◦ 情况2:原有空间之后没有⾜够⼤的空间 情况1 当是情况1 的时候,要扩展内存就直接原有内存之后直接追加空间...= NULL) { ptr = p; } //释放 free(p); p = NULL; return 0; } 我们把realloc的返回值返回个我们设置指针,然后判断不为NULL再赋值给

    11310

    开发成长之路(6)-- C++从入门到开发(C++入门不难)

    private: // 私有成员,只能在本类内使用,友元函数也行 }; 我们一般某些必须开放的接口设置公有,有些看情况设置保护,其余一律设为私有。...} }; ---- 构造/析构函数 初始化类的对象的时候会需要用到类的构造函数,构造函数的名称与类的名称是完全相同的,并且不会返回任何类型、 构造函数可用于某些成员变量设置初始值。...使用 new 运算符来任意的数据类型动态分配内存的通用语法: new data-type; 使用 delete 操作符释放它所占用的内存: delete pvalue; // 释放 pvalue...所指向的内存 示例: double* pvalue = NULL; // 初始化为 null指针 pvalue = new double; // 变量请求内存 balabala delete...pvalue; // 释放 pvalue 所指向的内存 ---- 数组的动态内存分配 直接上手吧: char* pvalue = NULL; // 初始化为 null指针 pvalue

    75820
    领券