Comme d'autres l'ont dit, mais en se concentrant sur les exceptions, il s'agit en fait d'une gestion ambiguë du transfert de contrôle.
Dans votre esprit, vous pensez probablement à un scénario comme celui-ci :
public static object SafeMethod()
{
foreach(var item in list)
{
try
{
try
{
//do something that won't transfer control outside
}
catch
{
//catch everything to not throw exceptions
}
}
finally
{
if (someCondition)
//no exception will be thrown,
//so theoretically this could work
continue;
}
}
return someValue;
}
Théoriquement, vous pouvez suivre le flux de contrôle et dire, oui, c'est "ok". Aucune exception n'est levée, aucun contrôle n'est transféré. Mais les concepteurs du langage C# avaient d'autres problèmes en tête.
L'exception rejetée
public static void Exception()
{
try
{
foreach(var item in list)
{
try
{
throw new Exception("What now?");
}
finally
{
continue;
}
}
}
catch
{
//do I get hit?
}
}
Le redoutable Goto
public static void Goto()
{
foreach(var item in list)
{
try
{
goto pigsfly;
}
finally
{
continue;
}
}
pigsfly:
}
Le retour
public static object ReturnSomething()
{
foreach(var item in list)
{
try
{
return item;
}
finally
{
continue;
}
}
}
La rupture
public static void Break()
{
foreach(var item in list)
{
try
{
break;
}
finally
{
continue;
}
}
}
Donc en conclusion, oui, bien qu'il y ait est a léger possibilité d'utiliser un continue
dans les situations où le contrôle n'est pas transféré, mais une bonne partie (la majorité ?) des cas impliquent des exceptions ou des changements de comportement. return
blocs. Les concepteurs du langage ont estimé que cela serait trop ambigu et (probablement) impossible à garantir au moment de la compilation que votre continue
est utilisé uniquement dans les cas où le flux de contrôle n'est pas transféré.
7 votes
Alors. Je suis juste curieux. Si vous comprenez parfaitement pourquoi il ne compile pas, pourquoi voulez-vous que quelqu'un vous explique ce qui a déjà du sens ? =)
14 votes
Pourquoi auriez-vous besoin d'un
continue;
surfinally
bloc ? n'est-ce pas la même chose quecontinue;
après letry -- catch
bloc ?0 votes
Probablement parce que ça ne sert à rien, c'est la dernière chose qui va arriver.
0 votes
Y a-t-il une faute de frappe dans l'échantillon (
do
) ?6 votes
@J.Steen Non, je sais vraiment que la
finally/continue
est une limitation du compilateur C# :-) Je suis également curieux de connaître la raison de cette limitation.0 votes
Bansi, oui c'est exactement ce que je fais pour résoudre la situation. J'étais juste surpris que ça ne fonctionne pas
0 votes
@xanatos Je voulais juste parler de la faute de frappe dans le code. D'habitude, il est recommandé de la laisser, mais comme elle était si évidemment une faute de frappe qui n'avait rien à voir avec la question, j'ai changé d'avis et n'ai pas voulu laisser de commentaire à ce sujet.
0 votes
J. Steen, CodeCaster modifié et cela a du sens maintenant :P
0 votes
Bien. ;) La clarté est la clé !
0 votes
@bansi, lpaloub : non, ce n'est pas du tout la même chose. Un continue ; après le try ne s'exécute pas si vous obtenez une exception non attrapée.
5 votes
@xanatos - Techniquement parlant, il s'agit d'une limitation du CIL sous-jacent. De la spécification linguistique : "Le transfert de contrôle n'est jamais autorisé à entrer dans un gestionnaire d'attrape ou une clause finale, sauf par le mécanisme de traitement des exceptions." et "Le transfert de contrôle hors d'une région protégée n'est autorisé que par une instruction d'exception (leave, end.filter, end.catch, ou end.finally)." Le site
br
La famille des instructions de branchement ne peut pas accomplir cela.1 votes
@Unsigned : c'est une bonne limitation aussi, permettre cela serait bizarre :)
0 votes
Continuer dans finalement sera autorisé à partir de Python 3.8