如何使用 goto 跳转到 for 循环的末尾,但不离开它
How to jump to the end of a for loop, but not leaving it, with goto
我有一个函数可以找到向量中的所有多个元素。如果我发送 {1,2,3,4,5,1,2,3,3,7}
它 returns {1,2,3}
。
我的输入向量有大约 100 到 10000 个元素,但我希望只有很少的不同(!)重复项;大约 1-5%。
因此,如果我已经将某个元素识别为多次出现,我会检查我的重复向量。如果是这样,函数将继续到下一个元素(如果有的话)。为此,我使用 goto
.
但是我需要在goto label
之后有一个命令。否则编译器会抱怨。有什么办法可以避免这种情况并保留 goto 吗?我知道我可以使用其他方法,例如相应地设置 bool 并使用 if()。但是我认为 goto 方法很简单。
vector<int> findDublicates(vector<int> const& v) {
// e.g. {1,2,3,4,5,1,2,3,7} -> {1,2,3}
vector<int> dublicates;
for (auto it(v.begin()); it != v.end() - 1;
++it) { // go through each element except the last
for (auto const& i :
dublicates) { // check if this is already a known dublicate
if (i == *it)
goto nextElement; // if so, goto the next element in v
}
for (auto it2(it + 1); it2 != v.end();
++it2) { // else compare it with the "not checked" elements in v
if (*it == *it2) { // if a dublicate is found, keep it
dublicates.emplace_back(*it);
break; // check the next element in v; could also use goto
// nextElement
}
}
nextElement:
cout << " "; // if I remove cout it won't compile: "expected
// primary-expression before '}' token"
}
return dublicates;
}
您应该可以使用分号作为空操作。
nextElement:
;
}
但是,我不确定您查找重复项的方法是否有效。您最好对数组进行排序,然后迭代一次。对向量进行排序会将所有重复项组合在一起。然后你只需检查当前元素是否与前一个元素相同。
如果删除 goto
不会杀死你,请尝试使用布尔辅助变量:
for(auto it(v.begin()); it!=v.end()-1; ++it) { //go through each element except the last
bool found = false;
for(auto const &i : dublicates) { //check if this is already a known dublicate
if(i==*it)
{
found = true;
break;
}
}
if (!found)
{
for(auto it2(it+1); it2!=v.end(); ++it2) { //else compare it with the "not checked" elements in v
if(*it==*it2) { //if a dublicate is found, keep it
dublicates.emplace_back(*it);
break; //check the next element in v; could also use goto nextElement
}
}
}
cout<<" "; //if I remove cout it won't compile: "expected primary-expression before '}' token"
}
goto
的使用在编程中被认为是错误的形式。在网络上搜索 "spaghetti code goto"。
我建议重组您的代码以不使用 goto。 Goto 可能很有用,但不受欢迎,通常可以用更具可读性的结构代替。
考虑:
bool isDublicate( int candidate, vector<int> const & dublicates )
{
for ( auto const &i: dublicates )
if ( i == candidate ) return true;
return false;
}
vector<int> findDublicates(vector<int> const &v) {
//e.g. {1,2,3,4,5,1,2,3,7} -> {1,2,3}
vector<int> dublicates;
for(auto it(v.begin()); it!=v.end()-1; ++it) { //go through each element except the last
if ( isDublicate( *it, dublicates ) )
continue;
for(auto it2(it+1); it2!=v.end(); ++it2) { //else compare it with the "not checked" elements in v
if(*it==*it2) { //if a dublicate is found, keep it
dublicates.emplace_back(*it);
break; //check the next element in v; could also use goto nextElement
}
}
}
return dublicates;
}
我有一个函数可以找到向量中的所有多个元素。如果我发送 {1,2,3,4,5,1,2,3,3,7}
它 returns {1,2,3}
。
我的输入向量有大约 100 到 10000 个元素,但我希望只有很少的不同(!)重复项;大约 1-5%。
因此,如果我已经将某个元素识别为多次出现,我会检查我的重复向量。如果是这样,函数将继续到下一个元素(如果有的话)。为此,我使用 goto
.
但是我需要在goto label
之后有一个命令。否则编译器会抱怨。有什么办法可以避免这种情况并保留 goto 吗?我知道我可以使用其他方法,例如相应地设置 bool 并使用 if()。但是我认为 goto 方法很简单。
vector<int> findDublicates(vector<int> const& v) {
// e.g. {1,2,3,4,5,1,2,3,7} -> {1,2,3}
vector<int> dublicates;
for (auto it(v.begin()); it != v.end() - 1;
++it) { // go through each element except the last
for (auto const& i :
dublicates) { // check if this is already a known dublicate
if (i == *it)
goto nextElement; // if so, goto the next element in v
}
for (auto it2(it + 1); it2 != v.end();
++it2) { // else compare it with the "not checked" elements in v
if (*it == *it2) { // if a dublicate is found, keep it
dublicates.emplace_back(*it);
break; // check the next element in v; could also use goto
// nextElement
}
}
nextElement:
cout << " "; // if I remove cout it won't compile: "expected
// primary-expression before '}' token"
}
return dublicates;
}
您应该可以使用分号作为空操作。
nextElement:
;
}
但是,我不确定您查找重复项的方法是否有效。您最好对数组进行排序,然后迭代一次。对向量进行排序会将所有重复项组合在一起。然后你只需检查当前元素是否与前一个元素相同。
如果删除 goto
不会杀死你,请尝试使用布尔辅助变量:
for(auto it(v.begin()); it!=v.end()-1; ++it) { //go through each element except the last
bool found = false;
for(auto const &i : dublicates) { //check if this is already a known dublicate
if(i==*it)
{
found = true;
break;
}
}
if (!found)
{
for(auto it2(it+1); it2!=v.end(); ++it2) { //else compare it with the "not checked" elements in v
if(*it==*it2) { //if a dublicate is found, keep it
dublicates.emplace_back(*it);
break; //check the next element in v; could also use goto nextElement
}
}
}
cout<<" "; //if I remove cout it won't compile: "expected primary-expression before '}' token"
}
goto
的使用在编程中被认为是错误的形式。在网络上搜索 "spaghetti code goto"。
我建议重组您的代码以不使用 goto。 Goto 可能很有用,但不受欢迎,通常可以用更具可读性的结构代替。
考虑:
bool isDublicate( int candidate, vector<int> const & dublicates )
{
for ( auto const &i: dublicates )
if ( i == candidate ) return true;
return false;
}
vector<int> findDublicates(vector<int> const &v) {
//e.g. {1,2,3,4,5,1,2,3,7} -> {1,2,3}
vector<int> dublicates;
for(auto it(v.begin()); it!=v.end()-1; ++it) { //go through each element except the last
if ( isDublicate( *it, dublicates ) )
continue;
for(auto it2(it+1); it2!=v.end(); ++it2) { //else compare it with the "not checked" elements in v
if(*it==*it2) { //if a dublicate is found, keep it
dublicates.emplace_back(*it);
break; //check the next element in v; could also use goto nextElement
}
}
}
return dublicates;
}