当我练习排序算法时,发现关于for each
的怪异问题。我不确定哪里出了问题,因此将整个代码发布在下面:
#include <algorithm>
#include <functional>
template <class T, class U = std::greater<>> // std::greater<> require C++14
void bubbleSort(T begin, T end, U comp = U())
{
for(auto i = end; i != begin; i--) {
for(auto j = begin; j != i; j++) {
if(comp(*j, *i)) {
std::swap(*j, *i);
}
}
}
}
template <class T, class U = std::greater<>> // std::greater<> require C++14
void bubbleSort2(T begin, T end, U comp = U())
{
auto low = begin;
auto high = end;
while(low < high) {
for(auto i = low; i != high; i++) {
if(comp(*i, *(i + 1))) {
std::swap(*i, *(i + 1));
}
}
high--;
for(auto i = high; i != low; i--) {
if(comp(*(i - 1), *i)) {
std::swap(*i, *(i - 1));
}
}
low++;
}
}
问题来了:
int main()
{
std::array<int, 10> s = {5, 7, 4, 2, 8, 6, 1, 9, 0, 3};
bubbleSort(s.begin(), s.end());
for(auto i = 0; i < s.size(); i++) // Loop1
std::cout << s.at(i) << " ";
std::cout << std::endl;
for (auto a : s) { // Loop2
std::cout << a << " ";
}
return 0;
}
起初,我只写了Loop2
来测试输出,但是观察到输出是:0 1 2 2 3 4 5 6 7 8
。然后添加Loop1
,输出将正确:
0 1 2 3 4 5 6 7 8 9
0 1 2 3 4 5 6 7 8 9
。我认为排序函数应该有问题,但是为什么添加Loop1
可以解决此问题?
(两种都具有相同的行为)
编译器是mingw32。
感谢@FeiXiang的评论,将固定代码放在GitHub
然后@Aconcagua的建议更改为:
template <class T, class U = std::greater<>> // std::greater<> require C++14
void bubbleSort3(T begin, T end, U comp = U())
{
while(end != begin) {
for(auto i = std::next(begin); i != end; ++i)
if(comp(*(i - 1), *i))
std::swap(*(i - 1), *i);
end--;
}
}
答案 0 :(得分:0)
“ i”应从“ end-1”开始
for(auto i = end-1; i != begin; i--)
因为“ end”指向数组中最后一个元素的下一个pos。