89 votes

Dans ce cas précis, est-il une différence entre l'utilisation d'un initialiseur de membre de la liste et attribuer une valeur à un constructeur?

En interne et sur le code généré, est-il vraiment une différence entre :

MyClass::MyClass(): _capacity(15), _data(NULL), _len(0)
{
}

et

MyClass::MyClass()
{
  _capacity=15;
  _data=NULL;
  _len=0
}

merci...

77voto

stefanB Points 27796

Vous devez utiliser la liste d'initialisation pour initialiser constante de membres,des références et de la classe de base

Lorsque vous avez besoin d'initialiser constante membre, des références et de passer des paramètres à la base de constructeurs de classe, comme mentionné dans les commentaires, vous devez utiliser la liste d'initialisation.

struct aa
{
    int i;
    const int ci;       // constant member

    aa() : i(0) {} // will fail, constant member not initialized
};

struct aa
{
    int i;
    const int ci;

    aa() : i(0) { ci = 3;} // will fail, ci is constant
};

struct aa
{
    int i;
    const int ci;

    aa() : i(0), ci(3) {} // works
};

Exemple (non exhaustif) class/struct contient référence:

struct bb {};

struct aa
{
    bb& rb;
    aa(bb& b ) : rb(b) {}
};

// usage:

bb b;
aa a(b);

Et l'exemple de l'initialisation de la classe de base qui nécessite un paramètre (par exemple, pas de constructeur par défaut):

struct bb {};

struct dd
{
    char c;
    dd(char x) : c(x) {}
};

struct aa : dd
{
    bb& rb;
    aa(bb& b ) : dd('a'), rb(b) {}
};

59voto

templatetypedef Points 129554

En supposant que ces valeurs sont des valeurs de types primitifs, alors non, il n'y a pas de différence. Initialisation des listes de seulement faire une différence lorsque vous avez des objets en tant que membres, puisqu'au lieu de l'utilisation d'initialisation par défaut suivie par cession, la liste d'initialisation permet d'initialiser l'objet de sa valeur finale. Cet état de fait peut être beaucoup plus rapide.

18voto

Richard Cook Points 10763

Oui. Dans le premier cas, vous pouvez déclarer _capacity, _data et _len comme des constantes:

class MyClass {
private:
    const int _capacity;
    const void *_data;
    const int _len;
// ...
};

Cela pourrait être important si vous voulez vous assurer qu' const-ness de ces variables d'instance, alors que le calcul de leurs valeurs lors de l'exécution, par exemple:

MyClass::MyClass() : _capacity(someMethod()), _data(someOtherMethod()), _len(yetAnotherMethod()) {
}

const instances doit être initialisé dans la liste d'initialiseur ou les types de sous-jacents doivent fournir au public sans paramètre de constructeurs (dont le type primitif de le faire).

6voto

user929404 Points 392

Je pense que ce lien http://www.cplusplus.com/forum/articles/17820/ donne une excellente explication - en particulier pour ceux qui sont nouveaux à C++.

La raison pour laquelle intialiser les listes sont plus efficaces, c'est que dans le corps du constructeur, seules les affectations prendre place, pas d'initialisation. Donc, si vous avez affaire à un non-built-in type, le constructeur par défaut pour cet objet a déjà été appelée avant que le corps du constructeur a été saisi. À l'intérieur du corps du constructeur, de l'affectation d'une valeur à cet objet.

En effet, ceci est un appel au constructeur par défaut suivie par un appel à la copie-opérateur d'affectation. La initialiser la liste vous permet d'appeler le constructeur de copie directement, et cela peut parfois être beaucoup plus rapide (rappelons que l'initialiser la liste est avant le corps du constructeur)

5voto

Fred Larson Points 27404

J'ajouterai que si vous avez des membres de type classe sans constructeur par défaut disponibles, l'initialisation est la seule façon de construire votre classe.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X