140 votes

do {...} while(false)

Je regardais le code d'un individu et j'ai remarqué qu'il semblait avoir un modèle dans ses fonctions :

<return-type> function(<params>)
{
 <initialization>

 do
 {
   <main code for function>
 }
 while(false);

 <tidy-up & return>
}

Ce n'est pas mauvais Il s'agit d'un problème très particulier (le code actuel est assez propre et sans surprise). Ce n'est pas quelque chose que j'ai vu avant et je me demande si quelqu'un peut penser à une logique derrière cela - un contexte dans un langage différent peut-être ?

3 votes

Avez-vous essayé de le remplacer par la version "normale" et de voir s'il compile toujours ? S'il ne compile pas lorsqu'il est écrit normalement, l'erreur du compilateur pourrait donner un indice sur la raison de ce changement.

12 votes

Pourquoi ne pas poser la question à l'"individu" plutôt que de nous demander de deviner son intention ?

1 votes

Peut-être que son professeur a exigé qu'il utilise un do...while() et il a utilisé ce code comme modèle de fonction depuis.

197voto

Thomas Eding Points 8651

Vous pouvez break de do{...}while(false) .

0 votes

Très bon point. Je n'y avais pas pensé. Utiliser des gotos sans utiliser "goto" :D

99 votes

+1 parce que c'est probablement l'intention du code, mais faire quelque chose comme ça est juste un goto déguisé de manière idiote. Si vous pensez qu'un goto est le bon outil pour ce travail, alors vous devriez juste utiliser un #$(*#@ goto.

3 votes

Ou continue . Mais je ferais mieux d'utiliser des éléments imbriqués if à la place.

141voto

Ben Voigt Points 151460

Beaucoup de gens font remarquer qu'il est souvent utilisé avec break comme une façon maladroite d'écrire "goto". C'est probablement vrai si elle est écrite directement dans la fonction.

Dans une macro, par contre, do { something; } while (false) est un moyen pratique de FORCER un point-virgule après l'invocation de la macro, absolument aucun autre jeton n'est autorisé à suivre.

Une autre possibilité est qu'il y a déjà eu une boucle à cet endroit ou qu'il est prévu d'ajouter l'itération à l'avenir (par exemple, dans le cadre du développement piloté par les tests, l'itération n'était pas nécessaire pour réussir les tests, mais logiquement, il serait logique de boucler à cet endroit si la fonction devait être un peu plus générale que ce qui est actuellement requis).

23 votes

+1 pour avoir mentionné l'utilité de ceci dans les macros ; je suis surpris que personne d'autre ne l'ait mentionné !

7 votes

Oui, le truc de la macro est en fait une utilisation parfaitement valide de ceci. Bien sûr, en dehors des macros, c'est juste idiot... ;)

13 votes

Ce n'est pas gênant, c'est utile, parce que c'est un Scoped goto - cela signifie que toutes les variables que vous déclarez dans la boucle do sont détruites, alors que le goto ne le fait pas.

27voto

Hogan Points 30189

La pause comme goto est probablement la réponse, mais je vais proposer une autre idée.

Il a peut-être voulu avoir des variables définies localement et a utilisé cette construction pour obtenir une nouvelle portée.

Rappelez-vous que le C++ récent permet {...} n'importe où, cela n'a pas toujours été le cas.

32 votes

Il aurait pu simplement utiliser des accolades dans ce cas.

2 votes

@Nemanja, vous seriez surpris du nombre de développeurs qui ne le savent pas et qui essaient quelque chose de similaire à ce que Hogan suggère.

8 votes

@Polaris @Nemanja, ce n'est qu'après 4 ans de programmation en C/C++ que j'ai compris que l'on pouvait créer une nouvelle portée locale. {} partout .. C'est particulièrement pratique dans switch-case code

23voto

Cameron Points 32208

Je l'ai vu utilisé comme un modèle utile lorsqu'il y a de nombreux points de sortie potentiels pour la fonction, mais le même code de nettoyage est toujours nécessaire, quelle que soit la façon dont la fonction sort.

Cela peut rendre un arbre if/else-if fastidieux beaucoup plus facile à lire, en ayant juste à interrompre chaque fois qu'un point de sortie est atteint, avec le reste de la logique en ligne ensuite.

Ce modèle est également utile dans les langages qui ne comportent pas d'instruction goto. C'est peut-être là que le programmeur original a appris ce modèle.

16 votes

Il suffit alors d'utiliser un goto honnête et direct au lieu d'un goto à peine déguisé.

4 votes

J'aime mieux cette façon de faire. Il est facile à lire et ne porte pas le stigmate d'un goto.

8 votes

Les gotos sont parfaitement lisibles s'ils sont utilisés avec parcimonie et localement. Ils doivent leur stigmatisation à l'époque où ils constituaient la principale forme de contrôle de flux et sautaient sur des centaines de lignes.

12voto

Brian Young Points 888

J'ai vu du code comme ça pour que vous puissiez utiliser break en tant que goto en quelque sorte.

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