Considerate questo codice (VS2008):Goto prima inizializzazione delle variabili provoca errore di compilatore
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);
}
}
Se è importante: questo è il codice da un compito a casa utilizzato per filtrare e modificare parole in un documento. document
tiene il documento (in precedenza leggere dal file)
Vorrei introdurre un goto dannoso perché penso che in realtà è più pulita, in questo caso in questo modo:
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);
}
}
o meno questa è una scelta buon design è irrilevante in questo momento. Il compilatore si lamenta error C2362: initialization of 'words' is skipped by 'goto SkipAndRestart'
Non capisco questo errore. Perché è importante, e un errore, che l'inizializzazione delle parole venga saltata? Questo è esattamente quello che voglio succedere, non voglio che faccia più lavoro, basta riavviare il ciclo insanguinato. La macro continua non fa più o meno esattamente la stessa cosa?
Avrei pensato che sarebbe stato solo un avvertimento, non un errore. Cosa succede se usi semplicemente 'break' invece del goto? –
La maggior parte delle persone probabilmente non sarebbe d'accordo sul fatto che la versione 'goto' è" più pulita "! –
@Oli: lo so, è per questo che ho detto che il design attuale della cosa è irrilevante; Non voglio iniziare una guerra di fiamme: P @ Paul: Compiles. – IAE