【问题标题】:Logical error in a C++ selection sort algorithm?C ++选择排序算法中的逻辑错误?
【发布时间】:2020-02-24 22:37:00
【问题描述】:

我是 C++ 新手,正在尝试编写这个简单的选择排序函数。如果对更有经验的编码人员来说答案很简单,我很抱歉,但我是初学者并且一直盯着这个问题很长时间无济于事。这是我的代码:

#include <iostream>
#include <array>
using namespace std;
array<int, 10> unsorted {3, 4, 1, 5, 7, 2, 8, 9, 6, 0};

void printarray(array<int, 10> arr) {
    int count = 0;
    for (int i : arr) {
        if (count < arr.size()-1) {
            cout << i << ", ";
        } else {
            cout << i << endl;
        }
        count++;
    };
}

int selection_sort(array<int, 10> arr) {
    int test;
    array<int, 10> newarr;
    for(int j = 0; j < arr.size(); j++) {
        test = arr[j];
        for(int i = j; i < arr.size(); i++) {
            if(arr[i+1] < test) {
                test = arr[i];
            }
        }
        newarr[j] = test;
    }
    printarray(newarr);
    return 0;
}


int main() {
    selection_sort(unsorted);
    return 0;
}

当我运行这个函数时,它会打印一个包含 10 个零的 int 数组。我为数组赋值的方式(在 C++ 中)是否存在错误,或者逻辑本身是否存在问题?

【问题讨论】:

  • 听起来你可能需要学习如何使用调试器来单步调试你的代码。使用好的调试器,您可以逐行执行您的程序,并查看它与您期望的偏差在哪里。如果您要进行任何编程,这是必不可少的工具。进一步阅读:How to debug small programsDebugging Guide
  • arr 中的值是什么?如果最小值在arr 的末尾,它将被复制到每个元素中
  • 除了 NathanOliver 关于调试的建议,我们还需要minimal reproducible example 来回答您的问题。这应该包括一个main() 函数,说明如何调用selection_sort() 函数。
  • @AlanBirtles 事实上最后一个值是零! arr 的值为 {3, 4, 1, 5, 7, 2, 8, 9, 6, 0}。现在这绝对是有道理的,我看到了那里的逻辑错误,谢谢!
  • if(arr[i+1] &lt; test) 的一些错误。当i 达到最大值arr.size() - 1 时,arr[i+1] 将越界。

标签: c++ arrays sorting logic


【解决方案1】:

这两个实现都是错误的。我刚刚纠正了@Adrisui3 的回答。 正确解决方案:

#include<iostream>
#include<vector>

using namespace std;

int main()
{   
    vector<int> array(5);
    int aux;

    array[0] = 10;
    array[1] = 2;
    array[2] = 45;
    array[3] = -5;
    array[4] = 0;

    for(int i = 0; i < array.size(); i++)
    {
        int min = i;
        for(int j = i+1; j < array.size(); j++)
        {
            if(array[j] < array[min])
            {
                min = j;

            }
        }

        if (i != min)
        {
            aux = array[i];
            array[i] = array[min] ;
            array[min] = aux;
        }
    }
    for(int k = 0; k < array.size(); k++)
    {
        std::cout << array[k] << std::endl;
    }

}

参考:wikipidia

【讨论】:

    【解决方案2】:

    这是实现选择排序的一种非常奇怪的方式。据我所知,你在那里犯了几个错误。首先,您不能在第一个 for 循环中使用 arr.size() ,因为它会导致第二个循环超出限制,从而导致意外行为。如果碰巧这些是常规数组,您会得到一个很好的分段错误。即使您没有收到运行时错误,您也需要注意这一点。 另一方面,这里的主要问题是由您使用索引的方式造成的,以及您实际上并不需要第二个数组这一事实。

    这里有一个这个算法的例子。

    #include<iostream>
    #include<vector>
    
    using namespace std;
    
    int main()
    {   
        vector<int> array(5);
        int aux;
    
        array[0]=10;
        array[1]=2;
        array[2]=45;
        array[3]=-5;
        array[4]=0;
    
        for(int i=0; i<array.size()-1; i++)
        {
            for(int j=i+1; j<array.size(); j++)
            {
                if(array[j]<array[i])
                {
                    aux=array[j];
                    array[j]=array[i];
                    array[i]=aux;
                }
            }
        }
    }
    

    另外,我建议你使用vector而不是array,两者都是STL的容器,但是vector更加灵活和有用,虽然它会消耗一些额外的内存。

    我希望我的回答足够清楚。如果您需要任何额外的帮助,我在这里。祝你好运!

    【讨论】:

    • 嘿!你是对的,向量消耗更多的内存!我的错,对不起。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2019-04-24
    • 1970-01-01
    • 2015-03-31
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多