终于通过测试搞明白operator delete了!

23 篇文章 0 订阅

最近写了一个简单的学生管理系统的类  在内存管理的地方遇到了点麻烦,现在解决了,对operator delete有了更深入的了解!

先看一下代码.

头文件

#ifndef KEXIN
#define KEXIN

#include <iostream>
#include <new>

#endif

namespace mystd
{
  class cstudent
  {
  private:
    char * pname;
    int age;
    char * which_one_class;
    int number_of_class;           //学号
    char * paddress;
  public:
    cstudent(char * ="",int =0, char * ="", int =0,char * ="");

    cstudent(const cstudent &);

    cstudent & operator=(const cstudent &);

    ~cstudent(void)
    {
    
    };

    friend std::ostream & operator<<(std::ostream & , const cstudent &);
    friend std::istream & operator>>(std::istream & , cstudent &);

    char * get_name() const;
    int    get_age() const;
    char * get_class() const;
    int    get_number_of_class() const;
    char * get_address() const;

    bool   reset(char * ="",int =0, char * ="", int =0,char * ="");

  }; 

 

  class cclass
  {
  private:
    cstudent * pstudent;
    cstudent monitor;
    char * class_number;
    int    m_space;
    int    use;
    cclass & operator=(const & cclass);
    cclass(const & cclass);
  public:
    cclass(char * ,int ,const cstudent &);
   
    bool is_this_class(const cstudent &) const;
    bool add_student(const cstudent &);
    int  get_use() const;
    int  get_space() const;
    cstudent & get_monitor();
    bool resize(char * ,int , const cstudent & );

  };
}

 

CPP文件

 

#include "cstudent.h"
namespace mystd
{
 cstudent ::cstudent(char * a ,int b, char * c, int d,char * e)
 {
    pname=a;
    age=b;
    which_one_class=c;
    number_of_class=d;
    paddress=e;
 }

 cstudent ::cstudent (const cstudent & an):pname(an.pname) , age(an.age) ,which_one_class(an.which_one_class),
   number_of_class(an.number_of_class) , paddress(an.paddress)  {/*empty funtion*/}

 cstudent &  cstudent ::operator=(const cstudent & x)
 {
    pname=x.pname;
    age=x.age;
    which_one_class=x.which_one_class;
    number_of_class=x.number_of_class;
    paddress=x.paddress;
    return *this;
 }

 char * cstudent::get_name() const
 {
    return pname;
 }

 int    cstudent::get_age() const
 {
    return age;
 }

 char * cstudent::get_class() const
 {
    return which_one_class;
 }

 int    cstudent::get_number_of_class() const
 {
    return number_of_class;
 }

 char * cstudent::get_address() const
 {
    return paddress;
 }

 std::ostream & operator<<(std::ostream & out , const cstudent & object)
 {
           out<<object.pname<<std::endl
     <<object.age<<std::endl
     <<object.which_one_class<<std::endl
     <<object.number_of_class<<std::endl
     <<object.paddress<<std::endl;
    return out;
 }

 std::istream & operator>>(std::istream & in ,cstudent  & objecttwo)
 {
    std::cout<<"please put in name with this student!"<<std::endl;
    in>> objecttwo.pname;
    std::cout<<"please put in age with this student!"<<std::endl;
    in>> objecttwo.age;
    std::cout<<"please put in which one class of this student!"<<std::endl;
    in>> objecttwo.which_one_class;
    std::cout<<"please put in which number of class of this student!"<<std::ends<<'/n';
    in>> objecttwo.number_of_class;
    std::cout<<"please put in address of this student!"<<std::endl;
    in>> objecttwo.paddress;
    return in;
 }

 bool cstudent::reset(char * aa , int bb , char * cc , int dd , char * ee)
 {
    if (aa=="" && bb==0 && cc=="" && dd==0 && ee=="")
    {
     std::cout<<"please take five count with this funtion run!" << std::endl;
     return false;
    }

     pname=aa;
     age=bb;
     which_one_class=cc;
     number_of_class=dd;
     paddress=ee;

    return true;
 }

 

 cclass :: cclass (char * a_a,int b_b,const cstudent & c_c): class_number(a_a),
  pstudent(static_cast<cstudent *> (operator new( sizeof(cstudent)*b_b) ) ), monitor(c_c), m_space(b_b)
 {
    use=0;
 }

 bool cclass :: is_this_class(const cstudent & theone) const
 {
    return ( class_number==theone.get_class() );
 }

 bool cclass  :: add_student(const cstudent & theother)
 {
    if( use == m_space )
    {
      std::cout<<"sorry,no space store this student!"<<std::endl;
      return false;
    }

    cstudent * old= pstudent;

    for (int m=0; m<use ; m++)
    {
      
      ++old;
    }

    new (old) cstudent( theother );
    
    ++use;

    return true;

 }

 int cclass  ::  get_use() const
 {
    return use;
 }

 int cclass  ::  get_space() const
 {
    return m_space;
 }

 cstudent & cclass::get_monitor ()
 {
    return monitor;
 }

 bool cclass::resize(char * one , int two , const cstudent & three)
 {
    if (two<m_space)
    {
      std::cout<<"please give more space!"<<std::endl;
      return false;
    }
    if (one!=class_number)
    { 
      std::cout<<"the class number is error!"<<std::endl;
      return false;
    }
    if (monitor.get_name() != three.get_name())
    {
      std::cout<<"the monitor is not same"<<std::endl;
      std::cout<<"Do you decide to continue?"<<std::endl;
      std::cout<<"yes   //    no ?"<<std::endl;

      char yn;
      std::cin>>yn;

      if (yn != 'y')
      {
        std::cout<<"you decide to no!"<<std::endl;
        return false;
      }

      std::cout<<"the monitor will be reset!"<<std::endl;
    }


    cstudent * olddel=pstudent;

    for (int bb=0;bb<use;bb++)
    {
      olddel->~cstudent();
      ++olddel;
    }
  

   

    operator delete(pstudent);


   
    pstudent= static_cast<cstudent *> (operator new( sizeof(cstudent)*two) );

    monitor=three;

    m_space=two;

    return true;
 }

}

 

 

通过高手的指点,和自己的测试,终于明白OPERATOR DELETE ()的使用方法了.
使我确定VC中NEW.H是不提供 OPERATOR DELETE[]的. 
既然是成对使用,那编译器 或者 操作系统就一定在NEW是 对该指针申请的内存数量是知道的,即使是OPERATOR NEW 一个类型数组,在OPERATOR DELETE ()时只删除一次这个指针就可以了,因为操作系统在NEW时知道内存数量,所以之前把OPERATOR DELETE ()放在FOR 循环里是不对的.因为指针加后的内存已经被一次性释放了.
 
下面是我的测试程序 来证明一次性确实释放了整个数组占用的内存.
 
  
    operator delete(pstudent);
 
    std::cout<<pstudent->get_name();
 
或者
 
     operator delete(pstudent);
    std::cout<<   (++pstudent) ->  get_name();
 
都是不对的.++pstudent 在调用get_name()就是想知道删除PSTUDENT指针是不是把相临的几块同大小内存都删除了,结果是上边所说的那样的.
 
 
所以正确的代码应该是
cstudent * olddel=pstudent;
    for (int bb=0;bb<use;bb++)
    {
      olddel->~cstudent();
      ++olddel;
    }
 
  
    operator delete(pstudent);

先析构内存中的对象,在释放内存.
 
 
关于新加的这段内存管理代码如下:
 
bool cclass::resize(char * one , int two , const cstudent & three)
 {
    if (two<m_space)
    {
      std::cout<<"please give more space!"<<std::endl;
      return false;
    }
    if (one!=class_number)
    {
      std::cout<<"the class number is error!"<<std::endl;
      return false;
    }
    if (monitor.get_name() != three.get_name())
    {
      std::cout<<"the monitor is not same"<<std::endl;
      std::cout<<"Do you decide to continue?"<<std::endl;
      std::cout<<"yes   //    no ?"<<std::endl;
      char yn;
      std::cin>>yn;
      if (yn != 'y')
      {
        std::cout<<"you decide to no!"<<std::endl;
        return false;
      }
      std::cout<<"the monitor will be reset!"<<std::endl;
    }

    cstudent * olddel=pstudent;
    for (int bb=0;bb<use;bb++)
    {
      olddel->~cstudent();
      ++olddel;
    }
 
  
    operator delete(pstudent);

  
    pstudent= static_cast<cstudent *> (operator new( sizeof(cstudent)*two) );
    m;
    m_space=two;
    return true;
 }

 
 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值