1

prendre deux classes et leurs constructeurs comme exemples suivants:quels types de constructeurs peuvent être appliqués pendant la compilation comme optimisation, pour les objets avec une durée de stockage statique?

class One{ 
public: 
    One(int a,int b):adad1(a),adad2(b){} 
private: 
    int adad1; 
    int adad2; 
}; 
class Two{ 
public: 
    Two(int input[]){ 
    for (int i=0;i<10;i++) 
    araye[i]=input[i]; 
    } 
private: 
    int araye[10]; 
}; 

compte tenu des objets ayant une durée de stockage statique, je pense que la première constructeur peut être appliqué au cours de la compilation en raison de son corps sans fonction qui lui permet d'être converti en expression constante dans certains cas comme une optimisation, mais j'ai des doutes sur le second. Quoi qu'il en soit, existe-t-il une règle spécifiant quels types de constructeurs peuvent être appliqués pendant la compilation?

+2

Que voulez-vous dire par "pendant la compilation"? Tous se produisent à l'exécution. Si vous voulez dire "vraiment" au moment de la compilation, vous devez attendre le 'constexpr' qui vient avec C++ 0x. – AraK

Répondre

2

Il n'y a aucune garantie que l'un des deux est initialisé statiquement avant qu'un code d'exécution ne soit exécuté. Pour la première, il est facile d'y arriver, mais

class One{ 
public: 
    int adad1; 
    int adad2; 
}; 

// initialized statically, if a and b are constant-expressions 
One one = { a, b }; 

Comme dit un autre gars, constexpr dans C++ 0x permet constructeurs à exécuter de manière statique. Dans votre cas, cela fonctionnerait pour le premier cas, mais pas pour le second. Vous devrez vivre cela pour la seconde, aucune garantie n'est faite par le Standard. Mais le Standard permet toujours une implémentation pour l'optimiser en phase d'initialisation statique. Voir 3.6.2/2

Une mise en œuvre est autorisé à effectuer l'initialisation d'un objet de champ d'espace de noms avec la durée de stockage statique comme une initialisation statique, même si une telle initialisation ne doit être fait de manière statique, à condition que

  • la version dynamique de l'initialisation ne modifie pas la valeur de tout autre objet de la portée espace de noms avec la durée de stockage statique avant son initialisation, et
  • la version statique de l'initialisation produit la même valeur dans l'objet initialisé comme serait prod par l'initialisation dynamique si tous les objets qui ne doivent pas être initialisés statiquement ont été initialisés dynamiquement.

Si le tableau donné est approprié, votre constructeur ne peut pas violer ces règles. La norme montre un exemple, que j'ai expliqué dans more detail here. Pour l'achèvement, le code exemple ci-dessous

inline double fd() { return 1.0; } 
extern double d1; 
double d2 = d1; // unspecified: 
        // may be statically initialized to 0.0 or 
        // dynamically initialized to 1.0 

double d1 = fd(); // may be initialized statically to 1.0 

Comme vous le voyez, mettre les choses à initialisées plus tôt peut même aller avec des valeurs initiales modifiées s'il existe une certaine relation entre les variables.

+0

très belle description, mais pourquoi avez-vous dit au début avec certitude qu'aucun cas ne peut être fait au moment de la compilation si les règles peuvent encore permettre cela? – Pooria

+0

@Pooria vous ne savez pas si l'implémentation l'optimise. Je voulais dire que vous ne pouvez pas compter dessus (donc vous devez supposer que vous obtenez des problèmes d'ordre d'initialisation statique) –

+0

alors s'il vous plaît modifier votre première phrase pour résoudre l'ambiguïté. – Pooria

-1

Aucun constructeur n'est appliqué lors de la compilation. En fait, aucun code n'est en cours d'exécution au moment de la compilation.

+0

Préprocesseurs C, templates, sin, sqrt, log, addition, soustraction, assignations littérales à portée globale, 'MyMatrix3x3 mat {cos (90), - sin (90), 0, sin (90), cos (90), 0 , 0, 0, 1}; 'sont tous construits au moment de la compilation (partie de l'image exécutable) de sorte qu'ils n'ont pas besoin d'être générés lors de l'exécution. C'est l'une des principales raisons d'utiliser C/C++, car cela vous donne certaines promesses sur ce que vous pouvez faire pour compiler l'heure sans écrire vos propres préprocesseurs tout le temps si vous voulez garantir que le calcul est fait au moment de la compilation. – Dmitry

+0

Les préprocesseurs C ne sont pas du code exécuté, ils sont dupliqués et code spécialisé. Et aucun des autres exemples n'est du code qui est exécuté, ce sont des expressions mathématiques qui sont précalculées.De plus, aucun compilateur ne garantit que ceux-ci seront optimisés au moment de la compilation et dépendront des capacités du compilateur et des paramètres d'optimisation utilisés lors de la compilation. –

+0

qui est le code exécuté par temps de compilation. Ce n'est pas parce qu'il ne fait rien d'excitant qu'il n'est pas exécuté par le préprocesseur. Le préprocesseur C est un analogue plus faible que les fichiers c préprocesseurs php/asp/jsp lors de la compilation, les templates sont légèrement plus puissants car ils ont accès aux tables de temps de compilation C++ alors que les préprocesseurs n'ont pas besoin de générer les leurs. – Dmitry