【问题标题】:Why this Selection sort code in Cpp, not giving required Output为什么这个选择排序代码在 Cpp 中,没有给出所需的输出
【发布时间】:2014-10-29 20:07:58
【问题描述】:
#include<iostream>

using namespace std;
int min_arr(int arr[],int size);
void swap(int *,int *);
int main()
{
    int arr[10]={31,2,55,3,77,12,89,98,43,34},loc;
    int* arr1;
    arr1 = &arr[0];
    for(int i=0;i<10;i++)
    {
        for( int j=i;j<9;j++)
        {
            loc = min_arr(arr1,(10-i));
            swap(&arr[loc],&arr[i]);
            arr1++;
        }
    }   

    for(int i =0; i<10;i++)
        cout<<arr[i]<<endl;

    return 0;
}

int min_arr(int arr[],int size)
{
    int k=0;
    int temp=arr[0];
    for(int i=1;i<size;i++)
    {
        if(arr[i]<temp)
        {
            temp=arr[i];
            k=i;
        }   
    }

    return k;
}

void swap(int *a, int *b)
{
   int temp;
   temp=*a;
   *a=*b;
   *b=temp;
}  

为什么 Cpp 中的选择排序代码没有给出所需的输出?请找出漏洞!在进行过程中,我使用了两个函数来查找子数组的最小值。当我找到最小值时,我返回它的索引并交换子数组的第一个位置和最小值元素!

【问题讨论】:

    标签: c++ dev-c++


    【解决方案1】:

    重新排列代码并添加一些调试行后,很容易找出问题所在:

    • 首先,第二个循环(j循环)完全没有意义
    • 其次,loc 变量不是基于 0,而是基于 i(当您搜索 arr1,它由循环递增),所以 arr[loc] 应该是 arr[loc+i]

    更正、巧妙的缩进(这对于使游览代码易于阅读很重要)代码:

    #include<iostream>
    
    #define ARRAY_SIZE 10
    using namespace std;
    int min_arr(int arr[],int size);
    void swap(int *,int *);
    int main()
    {
        int arr[ARRAY_SIZE]={31,2,55,3,77,12,89,98,43,34},loc;
        int* arr1;
        arr1 = &arr[0];
        for( int i = 0; i < ARRAY_SIZE; i++ )
        {
            //for( int j = i; j<ARRAY_SIZE-1; j++ )
            {
                loc = min_arr(arr1,(ARRAY_SIZE-i));
                // for debug:
                //std::cout << "min found at " << loc << std::endl;
                swap(&arr[loc+i],&arr[i]);
    
                // for debug:
                //for( int i =0; i<ARRAY_SIZE; i++ )
                //  cout << arr[i] << " ";
                //cout << std::endl;
    
                arr1++;
            }
        }   
    
        for( int i =0; i<ARRAY_SIZE; i++ )
            cout<<arr[i]<<endl;
    
        return 0;
    }
    
    int min_arr( int arr[], int size )
    {
        int k=0;
        int temp=arr[0];
        for( int i=1; i<size; i++ )
        {
            if( arr[i] < temp )
            {
                temp=arr[i];
                k=i;
            }   
        }
        return k;
    }
    
    void swap(int *a, int *b)
    {
        int temp;
        temp=*a;
        *a=*b;
        *b=temp;
    }  
    

    它会输出:

    2
    3
    12
    31
    34
    43
    55
    77
    89
    98
    

    【讨论】:

    • 我不明白你所说的关于 loc 的内容。为什么它是 loc+i ?
    • loc 是 arr1 中最小值的位置。但是,由于 arr1 通过循环递增 arr1[loc] 实际上是 arr[loc+i] (因为 arr1 实际上是 arr+i)。
    【解决方案2】:

    在您的版本中,您只需使用超出为数组映射的区域的指针。

    首先,调用函数min_arr。它需要数组,而不是指针:

    loc=min_arr(arr,(10-i));
    

    第二,函数本身。你总是从数组的开头开始,这就是为什么已经排序的元素会被重新使用。

    int min_arr(int arr[],int size)
    {
    int k=10-size;
    int temp=arr[k];
    for(int i=k+1;i<10;i++)
    {
        if(arr[i]<temp)
        {
            temp=arr[i];
            k=i;
        }
        }
    
       return k;
    }
    

    【讨论】:

    • 我没明白这一点。首先:- 函数 min_arr() 已经采用数组参数。其次,我的函数从头开始,因为我正在解析数组 'arr1' 而不是 'arr' !我猜你所说的将消除对 'arr1' 的需要?
    • 是的,arr1 中不再需要了。我假设,您希望该函数与子数组一起使用,将指向相应元素的指针传递给它,但有几个问题:1) arr1 超出了为数组映射的区域,因为它是在内部循环 2 中引入的)您尝试使用函数 min_arr 中的子数组索引,但是然后您将 &arr[loc] (因此 loc 现在是原始数组中的索引)转移到交换这就是为什么我建议传递给 min_arr 原始数组和元素的索引,你想从那里开始寻找一分钟
    【解决方案3】:
    for(int i=0;i<10;i++)
      {
        for( int j=i;j<9;j++)  //shouldn't this be j < 10 ?
    ......
    

    【讨论】:

    • 很抱歉投了反对票,但是您应该在提出任何答案之前测试您的代码...实际上,这个 j 循环是毫无意义的,您的提议不会使代码工作...
    猜你喜欢
    • 2022-01-14
    • 1970-01-01
    • 1970-01-01
    • 2023-02-05
    • 2022-07-28
    • 2021-09-06
    • 2021-06-30
    • 1970-01-01
    • 2022-08-22
    相关资源
    最近更新 更多