C++: Ensemble bool valeur que s'il n'est pas
Je avoir le code de mon application C++ qui, généralement, fait ceci:
bool myFlag = false;
while (/*some finite condition unrelated to myFlag*/) {
if (...) {
//statements, unrelated to myFlag
} else {
//set myFlag to true, perhaps only if it was false before?
}
}
if (myFlag) {
//Do something...
}
La question que je me pose concerne le else
déclaration de mon code. Fondamentalement, ma boucle peut définir la valeur de myFlag de faux à vrai, basée sur une certaine condition n'étant pas remplie. Jamais le drapeau unset de true à false. Je voudrais savoir ce que l'état fait plus de sens pour les performances et peut-être que si cette question est en fait une non-question en raison de l'optimisation du compilateur.
myFlag = true;
OU
if (!myFlag) myFlag = true;
Normalement j'choix de l'ex-car il nécessite écrire moins de code. Cependant, j'ai commencé à imaginer que peut-être il a impliqué inutile d'écriture de la mémoire et, par conséquent, celle-ci serait inutile de prévenir par écrit si myFlag était déjà vrai. Mais, serait à l'aide de ce dernier, prendre plus de temps car il y a une instruction conditionnelle et donc de compiler du code en utilisant plus d'instructions?
Ou peut-être que je suis plus de la pensée que c'est trop...
Mise à JOUR de 1
Juste pour clarifier un peu...le but de mon dernier cas est de ne pas écrire dans la mémoire si la variable était déjà vrai. Ainsi, seulement écrire dans la mémoire, si la variable est fausse.
Généralement,
myFlag = true
sera plus rapide cependant lorsque vous voulez savoir ce qui est le plus rapide que vous avez de profil sur votre propre système.Vous serait tout simplement le remplacement d'un inutile d'écrire avec une inutile de lire et de direction, et devinez qui est plus lent.
La seule fois que vous devez à vous soucier de choses comme cela, c'est quand vous écrivez à des variables qui sont partagées avec d'autres threads. Si myFlag a été partagé (il n'est pas dans votre cas), puis écrit à indistinctement ferait le cache-ligne
dirty
qui serait snoop il de tous les autres cœurs qui peut avoir eu un clean
copie, et vous devez tenir compte de false sharing
- mais je suis pensée la réponse 🙂OriginalL'auteur ecbrodie | 2013-02-22
Vous devez vous connecter pour publier un commentaire.
Vous êtes presque certainement préférable d'utiliser simplement
myFlag = true;
.Sur le mieux que vous pouvez espérer de la
if (!myFlag) myFlag = true;
est que le compilateur remarquerez que leif
est hors de propos et de l'optimiser à l'écart. En particulier, laif
déclaration doit lire la valeur actuelle demyFlag
. Si la valeur n'est pas déjà dans le cache, cela signifie que l'instruction va se bloquer en attente pour la lecture des données à partir de la mémoire.En revanche, si vous venez d'écrire (sans test) la valeur peut être écrit dans une file d'attente d'écriture, et puis de plus en plus des instructions peut exécuter immédiatement. Vous n'obtiendrez pas un décrochage jusqu'à ce que vous lisez la valeur de myFlag (et en supposant que c'est de lire dans un délai raisonnable après l'écriture, il va probablement être encore dans le cache, le décrochage sera minime).
Oh, ouais, au moins en théorie (par exemple, si vous avez seulement l'écriture par le biais de la mise en cache). Les circonstances pour mener à écrire lent sont au-delà de "très probable", quelque part sur la frontière entre "extrêmement rare" et "purement théorique".
+1 Bien expliqué.
OriginalL'auteur Jerry Coffin
Vous vous rendez compte que le chèque est discutable droit? Si vous aveuglément mis à
true
et il n'a pas été défini, vous êtes réglage. Si elle était déjàtrue
, alors il n'y a pas de changement et que vous êtes pas réglage, de sorte que vous pouvez la mettre en œuvre comme:Concernant le potentiel d'optimisation, pour être en mesure de test, la valeur doit être dans le cache, donc plus le coût est déjà payé. D'autre part, la branche (si le compilateur ne pas optimiser le
if
loin, dont la plupart seront) peuvent avoir un impact plus important sur les performances.OriginalL'auteur David Rodríguez - dribeas
CPU-cycle sage, préférez
myFlag = true;
Pense à ce sujet: même si le compilateur ne fait aucune optimisation (pas vraiment probable), il faut uneasm
déclaration, et en passant par lesif
faut au moins 1asm
déclaration.Si juste aller avec la cession.
Et surtout, n'essayez pas de faire des hypothèses sur ces détails de bas niveau, spécifiques des optimisations du compilateur peut tout à fait aller à l'encontre de l'intuition.
ok, mais de toute façon vous devrez l'obtenir à partir de la mémoire afin d'évaluer la
if
, et alors il aura plus de chances de rester dans la mémoire cache. De sorte que l'accès à la mémoire est nécessaire dans les deux cas, sauf si c'est déjà dans le cache.OriginalL'auteur Mic
Vous êtes plus probable de penser le problème, comme d'autres déjà mentionné, permettez-moi de faire de même. La suite pourrait être plus rapide si vous pouvez vous permettre de doubler les états étrangers à
myFlag
. En fait, vous pouvez vous débarrasser demyFlag
. OK, nous y voilà:Comme avec tous l'optimisation de la performance: Mesurez, mesurez, mesurez!
OriginalL'auteur Daniel Frey
Il est spécifique à une architecture si
if (!myFlag) myFlag = true;
prendra plus de temps à s'exécuter que le simplemyFlag = true;
même sans aucune optimisation. Il y a des architectures (par exemple, https://developer.qualcomm.com/hexagon-processor) où les deux états ne prendra qu'un seul cycle d'exécution.La seule façon de trouver votre machine serait en mesure.
En tout cas
myFlag = true
sera toujours plus rapide ou plus ont le même temps d'exécution commeif (!myFlag) myFlag = true;
OriginalL'auteur A. K.
Cette question m'a donné des maux de tête trop alors j'ai tout simplement testé moi-même avec le code suivant (C#):
résultat:
comparer + 1 tiques
comparer - 1 tiques
set - 0 tiques
tout le temps, utilisé pour définir la valeur n'est sûrement pas de zéro, il montre que même une seule requête besoin de plus de temps que de définition de la variable.
OriginalL'auteur oachkatzl