首页 > 其他 > 详细

一个重载operator new的例子

时间:2020-06-08 14:55:58      阅读:58      评论:0      收藏:0      [点我收藏+]

------------恢复内容开始------------

这个代码来自effictive c++ 249页,用来在申请内存的时候在内存的前后两端加入标志,这样在发生访问越界的时候便于检查。

之所以要写这段代码是因为我觉得这段代码里面我觉得比较稀奇的地方。

 1 //重载operator new使得在分配内存的时候   在前后两端加入标志位
 2 class base{
 3 private:
 4     int val;
 5 public:
 6     static const int signature;
 7     typedef unsigned char Byte;
 8     base(int a) :val(a){}
 9     void* operator new(std::size_t size) throw(std::bad_alloc){
10         using namespace std;
11         cout << "int the operator new" << endl;
12         //第0步 确定待分配内存的大小  以字节计
13         int new_size = size + 2 * sizeof(int);
14         //第一步  分配内存
15         void *p = malloc(new_size); //得到新分配内存的指针
16         if (p == NULL) throw bad_alloc();
17         //第二步在起始点和终止点填值
18         *((int *)p) = signature;
19         *(int *)((Byte *)p + size + sizeof(int)) = signature;
20         return (void *)((Byte *)p + sizeof(int));
21     }
22 };
23 const int base::signature = 0xDEAFFFFF;
24
25 int _tmain(int argc, _TCHAR* argv[]){
26     
27     base *p = new base(10);
28     return 0;
29 }

运行结果:

技术分享图片

以上代码和书上的代码有一点点区别 

1 *(static_cast<int *>(p)) = signature;
2 *(reinterpret_cast<int *>(static_cast<Byte*>(p)+new_size-sizeof(int))) = signature;

这是c++风格的数距类型转换。下面对c++的各种数据类型转换做简要说明。

1 const_cast<T> (exp); //用于去除const属性
2 dynamic_cast<T> (exp); //派生类向基类的转换 或者说 安全向下转型
3 reinterpret_cast<T>(exp); //不改变存储为 改变解释 用于底层转换
4 static_cast<T> (exp); //强制执行隐式类型转换
 1 int _tmain(int argc, _TCHAR* argv[]){
 2     
 3     int a = 10;
 4     int *p = &a;
 5     std::cout << (int)(p) << std::endl;
 6     //std::cout << (static_cast<int>(p)) << std::endl;    // 不存在指针转换为int的隐式转换
 7     std::cout << (reinterpret_cast<int>(p)) << std::endl;
 8 
 9     double dd = 5.14;
10     float ff = 2.14;
11     std::cout << (static_cast<int>(dd)) << std::endl;
12     //std::cout << (reinterpret_cast<int>(ff)) << std::endl;  // 将存储float类型直接转换为int是不被允许的
13 
14     char *pc1 = reinterpret_cast<char *>(p);
15     //char *pc2 = static_cast<char *>(p);   // 不存在 int * 向 char *的隐式转换
16 
17     void *pc3 = NULL;
18     int *pp = NULL;
19     char *pc4 = static_cast<char *> (pc3);
20     //char *pc4 = static_cast<char *> (pp);  //  不存在 int * 向 char *的隐式转换
21 
22     return 0;  
23 }

关于上面的代码是存在问题的,问题在于:

在使用new的时候前面去除4直接存放int这样会导致后面的存储内容可能出现地址没对齐的情况。

所谓地址没对齐是指:存放数据的地址的位置不满住地址大小的整数倍。

如:int 型必须的地址必须是4的整数倍。   double 必须要求地址是8的整数倍。

一个重载operator new的例子

原文:https://www.cnblogs.com/xiongxinxzy/p/13065423.html

(0)
(0)
   
举报
评论 一句话评论(0
关于我们 - 联系我们 - 留言反馈 - 联系我们:wmxa8@hotmail.com
© 2014 bubuko.com 版权所有
打开技术之扣,分享程序人生!