Merci @le_viking,
Je m’aperçois que je ne maîtrise pas tout. Dés que j’ai un peu de temps, je revois tout ça.
Il ne me semble pas en avoir eu un.
On peut très bien initialiser une variable de type double sans décimale : double var = 5;
Mais c’est différent dans le cas d’un constructeur
Tu lui affectes la valeur 5 pas une variable double qui vaut 5. En C++ il y a toujours une vérification de typage. Je testerais à l'occasion car il est rare que l'on affecte directement une valeur dans un constructeur, la liste d'initialisation tient très bien ce rôle.
Bonne soirée
Non, c'est bien aussi le principe d'un constructeur, même pour les types de base.
Vous instanciez une variable var de type double et essayez de lui affecter un int (car 5 aura le type par défaut int).
Ce qu'il se passe, c'est que la conversion implicite de l'int en double se fait automatiquement sans erreur.
Par contre, si vous utilisez un constructeur qui attend un double, il est préférable de s'assurer que la valeur passée est bien de type double pour éviter toute confusion (rendre le programme lisible et ne pas dépendre des conversions implicite)
Partir des différents noms donnés aux constructeurs n'est pas une bonne base pour comprendre c'est purement une vision humaine que de vouloir nommer les choses.
Pour expliquer que le constructeur le plus simple que l'on puisse faire est un constructeur sans argument on va dire qu'il est par défaut, quand il contient un argument on va dire qu'il est de transtypage et ces termes deviennent génériques et ce n'est pas leur signification de base.
Et ceci en est un exemple
class MaClasse {
public:
MaClasse(int x=4) {}
};
MaClasse obj (5); //appel implicite avec un argument
MaClasse obj1 = 5; //opération de transtypage
MaClasse obj2; ///appel implicite sans argument
au premier objet c'est un constructeur avec un argument, au second un constructeur de transtypage et au troisième un constructeur par défaut
On n'utilise pas explicit, le transtypage et l'appel explicite en C++
explicit ne veut pas dire qu'il faut que le constructeur soit appelé explicitement, il est utilisé par les concepteurs pour "protéger" leur classe. En principe quand on crée sa classe pourquoi mettre explicit on sait comment l'utiliser.
Le transtypage ne présente aucun intérêt
L'appel explicite n'est pratiquement utilisé que lorsque l'appel peut prêter à confusion entre plusieurs constructeurs
Ma référence c’est la spécification du langage. Il y est dit par exemple
A default constructor is a constructor which can be called with no arguments
Donc il n’y a aucune interprétation possible, c’est la norme qui dit ce qu’est un constructeur par défaut, ce n’est pas « on va dire ».
Pour le transtypage (conversion) la Doc dit
A constructor that is not declared with the specifier explicit and which can be called with a single parameter(until C++11)is called a converting constructor.
It is said that a converting constructor specifies an implicit conversion from the types of its arguments (if any) to the type of its class. Note that non-explicit user-defined conversion function also specifies an implicit conversion.
Certes, le constructeur existe sans appel. Mais dans un soft si on crée complètement une classe .c et .h avec toutes ses méthodes, faute d'au moins un appel au constructeur le compilateur considérera que la classe n'existe pas et Il ignorera tout simplement le .h et .c
Oui, mais la dénomination est conceptuelle, la classe peut être une simple bibliothèque, pas dans une application et si on veut la décrire il faudra bien utiliser des mots. La spécification du langage nous donne ces mots (certes en anglais) et mon point est juste de dire qu’il vaut mieux - pour se faire comprendre - utiliser ces mots.
Fonction membre, constructeur par défaut, déclaration versus définition etc… Il y a des définitions pour cela.
Je suis tout à fait d'accord avec vous, on est bien obligé de mettre des mots sur les choses. L'un dira constructeur de copie et l'autre dira constructeur de recopie simplement parce que les enseignants utilisent leurs propres termes.
C'est une façon d'expliquer que par défaut le compilateur crée un constructeur par défaut. Dire constructeur par défaut par défaut ça résume bien la situation même si c'est un raccourci qui n'a rien d'officiel
Pour le coup pas vraiment, mais si je ne trouve pas cette façon de nommer très heureuse, mais comme je n'aime pas non plus ceux utilisé par la norme
L'idée de @le_viking je crois, c'est que le premier "par défaut" indique qu'il s'agit d'un constructeur sans paramètre, alors que le deuxième qu'il est ajouté par le compilateur.
c'est donc dans ce cas deux sens différents. Même effectivement un le constructeur ajouté par le compilateur a forcément aucun paramètre
Je comprends bien l’idée mais Pourquoi ne pas dire le constructeur par défaut implicite comme le fait la norme pour parler de celui fourni par le compilateur ?
Implicitly-declared default constructor
If there is no user-declared constructor or constructor template for a class type, the compiler will implicitly declare a default constructor as an inline public member of its class.
C’est quand même plus clair, non ?
De plus l’utilisation de ce mot permet de clarifier le mot clé explicit du langage. Ça rend le tout cohérent. (un constructeur implicite permet les conversions automatiques non désirées, tandis que le mot-clé explicit interdit ces conversions, justifiant ainsi l’introduction du terme implicite pour clarifier cette distinction.)
Pour clore ce débat je dirais que mon point de vue est que l’on a toujours à gagner à utiliser des mots très proches de la normes (de copie ou de recopie c’est OK par exemple) quand on enseigne le langage. Cela permet ensuite aux apprenants de s’y retrouver lorsqu’ils se plongent dans la doc peut être des années plus tard. Les mots comptent et maîtriser les concepts de bases et ce qu’ils portent aide énormément à comprendre ensuite un code ou une explication de code.
Je ne suis pas prof mais j’ai aidé et aide des apprenants et la majorité des difficultés que je vois (que ce soit en maths, physique, sciences, informatique,…) vient souvent d’une mauvaise compréhension de certains mots.
En les aidant à maîtriser ces mots souvent on assiste à un moment « eurêka » où vous voyez tout d’un coup que tout s’éclaire, chaque chose tombe à sa place.
Ce que l’on conçoit bien s’énonce clairement, et les mots pour le dire arrivent aisément.…
Je reviens sur le fil de discussion, j'ai quelques soucis de santé en ce moment, à priori je souffre d'un nystagmus lié à un problème d'oreille interne et du coup il m'est parfois difficile de lire et d'écrire ...
Ce matin c'est un peu mieux et j'ai refait l'exemple d'une classe avec appel d'un constructeur de conversion :
class Objet
{
public:
Objet(double LeChiffre); // constructeur avec un seul argument
double getLeChiffre() const; // fonction membre : accesseur ou "getter"
private:
double LeChiffre;
};
Objet::Objet(double LeChiffre) : LeChiffre(LeChiffre) {}
double Objet::getLeChiffre() const
{
return this->LeChiffre;
}
void setup() {
Serial.begin(115200);
Objet monInstance = 6.0; /*appel implicite du constructeur de conversion -
Conversion implicite du double 6,0 en Objet -
En fait on convertit le double 6.0 en un objet de type Objet*/
Serial.println(monInstance.getLeChiffre());
}
void loop() {
// put your main code here, to run repeatedly:
}
Je pense que cet exemple est conforme à tous points de vue aux remarques qui ont été faites ou du moins je l'espère.