Y a-t-il un appel que je peux passer à new
pour que la mémoire soit nulle comme calloc
?
Réponses
Trop de publicités?Contrairement à ce que certains disent, dans leurs réponses, il est possible.
char * c = new char[N]();
Va zéro initialiser tous les personnages (en réalité, il est appelé valeur d'initialisation. Mais la valeur d'initialisation va être zéro-initialisation pour tous ses membres d'un tableau de type scalaire). Si c'est ce que vous êtes après.
Vaut la peine de noter qu'il ne travaillons aussi pour des (ensembles de) classe-types sans utilisateur déclaré constructeur dans ce cas, les membres de leur valeur est initialisée:
struct T { int a; };
T *t = new T[1]();
assert(t[0].a == 0);
delete[] t;
Ce n'est pas une extension, ou de quelque chose. Il a travaillé et s'est comporté de la même façon en C++98 trop. Juste là, il a été appelé d'initialisation par défaut au lieu de la valeur d'initialisation. Zéro initialisation, cependant, se fait dans les deux cas pour des scalaires ou des tableaux de scalaires ou POD types.
Non, mais il est assez facile de créer une nouvelle version qui fonctionne comme calloc. Cela peut être fait de la même manière que la version sans lancement de new est implémentée.
SomeFile.h
struct zeromemory_t{};
extern const zeromemory_t zeromemory;
void* __cdcel operator new(size_t cbSize, const zeromemory_t&);
SomeFile.cpp
const zeromemory_t zeromemory;
void* _cdecl operator new(size_t cbSize, const zeromemory_t&)
{
void *mem = ::operator new(cbSize);
memset(mem,0,cbSize);
return mem;
}
Vous pouvez maintenant effectuer les opérations suivantes pour obtenir de nouveaux éléments avec une mémoire nulle
MyType* pMyType = new (zeromemory) MyType();
De plus, vous auriez besoin de faire d'autres choses amusantes comme définir de nouveaux [] qui est assez simple aussi.
Vous pourriez faire un mondial de la surcharge de l'opérateur new
et ont, prenez la mémoire brute d' calloc()
. De cette façon, la mémoire est essuyée avant constructeurs arriver à courir, donc il n'y a pas de problèmes là-bas.
Toute classe qui remplace de nouveau sur son propre ne sera pas obtenir votre spécial calloc()
base new
, mais alors que la classe doit être initialisé correctement de toute façon.
N'oubliez pas de remplacer les deux new
et delete
et le tableau des versions...
Quelque chose comme:
#include <exception> // for std::bad_alloc
#include <new>
#include <stdlib.h> // for calloc() and free()
void* operator new (size_t size)
{
void *p=calloc(size, 1);
if (p==0) // did allocation succeed?
throw std::bad_alloc();
return p;
}
void operator delete (void *p)
{
free(p);
}
void* operator new[] (size_t size)
{
void *p=calloc(size, 1);
if (p==0) // did allocation succeed?
throw std::bad_alloc();
return p;
}
void operator delete[] (void *p)
{
free(p);
}
Notez que ces versions ne sont pas tout à fait exactement ce qu'elles devraient être - l' new
opérateur doit exécuter dans une boucle de l'appel de la new_handler
(s'il est installé) et seulement jeter l' bad_alloc
exception si il n'y a pas d' new_handler
. Ou quelque chose comme ça, je vais avoir à le rechercher et de mettre à jour plus tard.
Oh, et vous pouvez aussi remplacer l' no_throw
version.