Considérez ce code (VS2008):avant l'initialisation des variables provoque une erreur du compilateur
void WordManager::formatWords(std::string const& document)
{
document_ = document;
unsigned int currentLineNo = 1;
size_t oldEndOfLine = 0;
size_t endOfLine = document_.find('\n');
while(endOfLine != std::string::npos)
{
std::string line = document_.substr(oldEndOfLine, (endOfLine - oldEndOfLine));
if(line.size() < 2)
{
oldEndOfLine = endOfLine + 1;
endOfLine = document_.find('\n', oldEndOfLine);
continue;
}
std::vector<std::string> words = Utility::split(line);
for(unsigned int i(0); i < words.size(); ++i)
{
if(words[i].size() < 2)
continue;
Utility::trim(words[i], WordManager::delims);
Utility::normalize(words[i], WordManager::replace, WordManager::replaceWith);
if(ruleOne(words[i]) && ruleTwo(words[i]))
{
std::set<Word>::iterator sWIter(words_.find(Word(words[i])));
if(sWIter == words_.end())
words_.insert(Word(words[i])).first->addLineNo(currentLineNo);
else
sWIter->addLineNo(currentLineNo);
}
}
++currentLineNo;
oldEndOfLine = endOfLine + 1;
endOfLine = document_.find('\n', oldEndOfLine);
}
}
S'il est important: ce code est d'une tâche de travail utilisé pour filtrer et modifier des mots dans un document. document
détient le document (lu précédemment du fichier)
Je souhaite introduire un goto malveillant parce que je pense qu'il est en fait plus propre dans ce cas comme ceci:
void WordManager::formatWords(std::string const& document)
{
document_ = document;
unsigned int currentLineNo = 1;
size_t oldEndOfLine = 0;
size_t endOfLine = document_.find('\n');
while(endOfLine != std::string::npos)
{
std::string line = document_.substr(oldEndOfLine, (endOfLine - oldEndOfLine));
// HERE!!!!!!
if(line.size() < 2)
goto SkipAndRestart;
std::vector<std::string> words = Utility::split(line);
for(unsigned int i(0); i < words.size(); ++i)
{
if(words[i].size() < 2)
continue;
Utility::trim(words[i], WordManager::delims);
Utility::normalize(words[i], WordManager::replace, WordManager::replaceWith);
if(ruleOne(words[i]) && ruleTwo(words[i]))
{
std::set<Word>::iterator sWIter(words_.find(Word(words[i])));
if(sWIter == words_.end())
words_.insert(Word(words[i])).first->addLineNo(currentLineNo);
else
sWIter->addLineNo(currentLineNo);
}
}
SkipAndRestart:
++currentLineNo;
oldEndOfLine = endOfLine + 1;
endOfLine = document_.find('\n', oldEndOfLine);
}
}
Que ce soit ou non un bon choix de conception est pas pertinent en ce moment. Le compilateur se plaint error C2362: initialization of 'words' is skipped by 'goto SkipAndRestart'
Je ne comprends pas cette erreur. Pourquoi est-il important, et une erreur, que l'initialisation des mots soit ignorée? C'est exactement ce que je veux arriver, je ne veux pas qu'il fasse plus de travail, il suffit de redémarrer la boucle sanglante. La macro continue ne fait-elle pas plus ou moins exactement la même chose?
J'aurais pensé que ce serait juste un avertissement, pas une erreur. Que se passe-t-il si vous utilisez juste 'break' au lieu du goto? –
La plupart des gens ne seraient probablement pas d'accord que la version 'goto' est" plus propre "! –
@Oli: Je sais, c'est pourquoi j'ai dit que la conception de la chose n'est pas pertinente; Je ne veux pas commencer une guerre de flamme: P @ Paul: compile. – IAE