众所周之, 在MFC Debug 程序由VC生成的cpp中 new 是进行了宏定义的
#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif
这样 分配内存的语句类似 int* pn = new int; 的就会被最终替换为 int* pn = new(THIS_FILE, __LINE__) int; 而被执行现在我想要重载new函数
void* AFX_CDECL operator new(size_t nSize, unsigned long dwMyData)
在某引些代码中使用这个重载的new函数
比如:
int* pn = new int; // 调用VC定义的new
DWORD* pn1 = new DWORD; // 这一句我想使用我重载的new函数, 那么这里的调用就应该是 DWORD* pn1 = new(dwMyData) DWORD;但现在问题来了,我使用DWORD* pn1 = new(dwMyData) DWORD;后发现编译不通过, 这是因为DEBUG版本宏定义使 new 被替换为 DEBUG_NEW, 最终这句代码变为
DWORD* pn1 = new(THIS_FILE, __LINE__)(dwMyData) DWORD;
当然就出错了我现在就想怎么能在 DEBUG版本下 能既支持VC定义的new函数, 又支持我定义的new函数呢?现在有一个觉得不大好的方法,就是写了一个 defMyNew.h
///////////////////////////////////
// defMyNew.h
#ifndef __DEFMYNEW_H__
#define __DEFMYNEW_H__void* AFX_CDECL operator new(size_t nSize, LPCSTR lpszFileName, int nLine, unsigned long dw)
{
// 我的实现代码
}template<class T> T* MyNew(T n)
{
return new(__FILE__, __LINE__, 0) T;
}#endif // __DEFMYNEW_H__
在使用时这样写
//////////////////////////////////////
// Test.cpp
#include "stdafx.h"
#include "Test.h"
#include "defMyNew.h"#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endifvoid Test()
{
int* pn = new int;
int* pn1 = MyNew(int())
DWORD* pdw = MyNew(DWORD());
}这样通过函数模板就可以兼容两个new函数的使用
但这种写法自已都觉得很怪异
希望大家发表一下各自的高见, 能更好的实现我的要求
#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif
这样 分配内存的语句类似 int* pn = new int; 的就会被最终替换为 int* pn = new(THIS_FILE, __LINE__) int; 而被执行现在我想要重载new函数
void* AFX_CDECL operator new(size_t nSize, unsigned long dwMyData)
在某引些代码中使用这个重载的new函数
比如:
int* pn = new int; // 调用VC定义的new
DWORD* pn1 = new DWORD; // 这一句我想使用我重载的new函数, 那么这里的调用就应该是 DWORD* pn1 = new(dwMyData) DWORD;但现在问题来了,我使用DWORD* pn1 = new(dwMyData) DWORD;后发现编译不通过, 这是因为DEBUG版本宏定义使 new 被替换为 DEBUG_NEW, 最终这句代码变为
DWORD* pn1 = new(THIS_FILE, __LINE__)(dwMyData) DWORD;
当然就出错了我现在就想怎么能在 DEBUG版本下 能既支持VC定义的new函数, 又支持我定义的new函数呢?现在有一个觉得不大好的方法,就是写了一个 defMyNew.h
///////////////////////////////////
// defMyNew.h
#ifndef __DEFMYNEW_H__
#define __DEFMYNEW_H__void* AFX_CDECL operator new(size_t nSize, LPCSTR lpszFileName, int nLine, unsigned long dw)
{
// 我的实现代码
}template<class T> T* MyNew(T n)
{
return new(__FILE__, __LINE__, 0) T;
}#endif // __DEFMYNEW_H__
在使用时这样写
//////////////////////////////////////
// Test.cpp
#include "stdafx.h"
#include "Test.h"
#include "defMyNew.h"#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endifvoid Test()
{
int* pn = new int;
int* pn1 = MyNew(int())
DWORD* pdw = MyNew(DWORD());
}这样通过函数模板就可以兼容两个new函数的使用
但这种写法自已都觉得很怪异
希望大家发表一下各自的高见, 能更好的实现我的要求
size_t count
);
void *__cdecl operator new(
size_t count,
void * object
) throw();
void *__cdecl operator new(
size_t count,
const std::nothrow_t&
) throw();
所以做模板没有必要
如果真想在debug版本中用自己的new的话,直接用宏替换掉DEBUG_NEW这个 换成原来的new就可以了还有一点 默认的new是线程安全的
// defMyNew.h
#ifndef __DEFMYNEW_H__
#define __DEFMYNEW_H__
#pragma warning(disable: 4800)
#pragma push_macro("new")
#undef newvoid* AFX_CDECL operator new(size_t nSize, LPCSTR lpszFileName, int nLine, unsigned long dw)
{
// 我的实现代码
} template <class T> T* MyNew(T n)
{
return new(__FILE__, __LINE__, 0) T;
} #pragma pop_macro("new")
#pragma warning(default: 4800)#endif // __DEFMYNEW_H__
//////////////////////////////////////
// Test.cpp
#include "stdafx.h"
#include "Test.h" #ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif
#include "defMyNew.h" // 换一个位置,放到#define new...的后面void Test()
{
int* pn = new int;
int* pn1 = MyNew(int())
DWORD* pdw = MyNew(DWORD());
}
如果是这样
int* pn = new int; 也被替换为我重载的new了, 像是不符合我的要求吧
做成模板只是让我的重载new不受Test.cpp宏定义的影响而不得不用的
你加上
#pragma pop_macro("new")
#pragma warning(default: 4800)
这些的目的是什么呢?加上后,基本的方法还是我的那个方法呀
#pragma warning(disable[default]: 4800) -----> 消除编译器的一个类型转换警告而已,可以不使用
没有必要加上这些吧?
不明白,解释一下
干嘛弄得这么乱啊。
new 除了内存分配外,还会自动地调用创建对象的构造函数
如果我定义mynew全局函数, 那只能实现内存的分配,不能调用对象的构造函数, 这和new的功能不符吧?
你看我的实现就是定义了一个函数MyNew,
使用模板的原因就是为了把要创建的类型传到MyNew里面
在里面使用真正的new 来分配内存,调用对象构造函数
调用构造函数也很简单,假设你在栈上构造一块内存用于CYourClass,要调用CYourClass的构造函数,你可以这样写:
BYTE buf[sizeof(CYourClass)]; // 栈上的内存块,或者用全局的也可以 BYTE* buf = new BYTE[sizeof(CYourClass)];
::new(buf) CYourClass(); // 这句就是调用构造函数
CYourClass* p = (CYourClass*)buf; // 现在可以用p了