仅使用 iostream 按字母顺序对 2d 数组进行气泡排序

Bubble sort 2d array in alphabetical order only using iostream?

本文关键字:数组 2d 排序 气泡 顺序 iostream      更新时间:2023-10-16

我正在尝试弄清楚如何按字母顺序对单词列表进行排序。我现在拥有的代码将正确排序它们,只有当每个单词只有 1 个字母时。一旦我移动到更多的字母,它就会失败。你能帮我解决这个问题吗?谢谢

我的输入文件是:

Emma
Liam
Dill
Bill
Kimm
Jacks
John
Hats
Julia
Jill

法典:

#include <iostream>
#include <fstream>
using namespace std;
void sort(char input[10][25], int size);
int main(){
    char input[10][25] = {"Emma", "Liam", "Dill", "Bill", "Kimm", "Jacks", "John", "Hats", "Julia", "Jill"};
    sort(input,10);
    cout << "Sorted:n";
    for(int i = 0; i < 10; i++){
        cout << input[i];
    }
    return 0;
}

void sort(char input[10][25],int size){
    char temp;
    for(int k = 0;k < 10;k++){
        for(int i = 0; i < 9; i++){
            for(int j = 0; j < 24; j++){
                if(input[i][j] > input[i+1][j]){
                    temp = input[i][j];
                    input[i][j] = input[i+1][j];
                    input[i+1][j] = temp;
                }
            }
        }
    }
}

代码的主要问题是,当一个单词需要与另一个单词交换时,不要交换数组中的两个单词。相反,您只交换第一个单词的字符,这些字符大于第二个单词的字符。这造成了混乱。

例如,当您尝试交换以下两行时

SALLY
MOMMA

您的最终结果是:

MALLA
SOMMY

另一个问题包括"John"和"Hats"之间缺少逗号,导致数组中只有9个条目,其中一个是"JohnHats"。

最后,冒泡排序需要在循环中使用不同的索引来保留已排序的元素。

使用帮助程序函数有助于更清楚地说明这一点。下面是一个示例解决方案,与您最初编写的解决方案很接近,但具有帮助程序函数。

#include <iostream>
#include <fstream>
using namespace std;
bool smaller(char input[10][25], int a_index, int b_index) {
    char* a = input[a_index];
    char* b = input[b_index];
    for (int i = 0; a[i] != 0 && b[i] != 0; i++) {
        cout << a[i] << " " << b[i];
        if (a[i] > b[i]) {
            return false;
        } else if (a[i] < b[i]){
            return true;
        }
    }
    return true;
}
void swap(char input[10][25], int a, int b) {
    for(int i = 0; i < 25; i++){
        char temp = input[a][i];
        input[a][i] = input[b][i];
        input[b][i] = temp;
    }
}
void sort(char input[10][25], int size){
    char temp;
    for(int k = 0; k < 10; k++){
        for(int i = k + 1; i < 10; i++){
            if (smaller(input, i, k)) {
                swap(input, i, k);
            }
        }
    }
}
int main(){
    char input[10][25] = {"Emma", "Liam", "Dill", "Bill", "Kimm", "Jacks", "John", "Hats", "Julia", "Jill"};
    sort(input,10);
    cout << "Sorted:n";
    for(int i = 0; i < 10; i++){
        cout << input[i];
    }
    return 0;
}

为了使代码更具可读性,让我们定义一个 swap 方法:

void Swap_Names(char a[25], char b[25])
{
  char c;
  for (unsigned int i = 0; i < 25; ++i)
  {
    c = a[i];
    a[i] = b[i];
    b[i] = c;
  }
}

比较函数可以使代码更具可读性:

bool Is_Less_Than(char a[25], char b[25])
{
  bool is_less = false;
  for (unsigned int 0 = 1; i < 25; ++i)
  {
    if (a[i] != b[i])
    {
       is_less = a[i] < b[i];
       break;
    }
  }
  return is_less;
}

气泡排序的工作原理是交换项目(在本例中为名称)。

void Bubble_Sort(char input[10][25], unsigned int size) // size can't be negative.
{
  bool swap_occurred = true;
  while (swap_occurred)
  {
    swap_occurred = false;
    for (unsigned int index = 0; index < 9; ++index)
    {
      if (! Is_Less_Than(input[index], input[index + 1]))
      {
        Swap_Names(input[index], input[index + 1]);
        swap_occurred = true;
      }
    }
  }
}

首先,你的代码中有一个UB:

string input[10] = {
        "Emma", "Liam", "Dill", "Bill", "Kimm",
        "Jacks", "John" "Hats", "Julia", "Jill"}; // a great problem here: 

"John" "Hats":缺少逗号会造成巨大的灾难。

您可以轻松使用类字符串而不是常量字符串数组,因此您只需比较数组中每个单词的首字母,并在条件为真时交换:

#include <iostream>
#include <string>
using namespace std;
void sort(string input[10]);

int main()
{
    string input[10] = {
        "Emma", "Liam", "Dill", "Bill", "Kimm",
        "Jacks", "John", "Hats", "Julia", "Jill"};
    sort(&input[0]);
    for(int i(0); i < 10; i++)
        cout << input[i] << ", ";
    cout << endl;
    return 0;
}

void sort(string input[10])
{
    for(int i = 0; i < 10; i++)
    {
        for(int j = i + 1; j < 10; j++)
        {
            if(toupper(input[i][0]) > toupper(input[j][0])) // I used `toupper()` to not distinguish between small and capital letters
            {
                string temp = input[i];
                input[i] = input[j];
                input[j] = temp;
            }
        }
    }
}
  • 如果你想要一个完整的比较,这意味着比较两个单词的第一个字母,如果它们相等,那么比较秒等等,你需要一些额外的工作或使用某些类的一些工具。

冒泡排序是一种糟糕的排序算法。

但它确实有一个优点,那就是它可以轻松地对你不保存在内存中的数据进行排序,只要你可以保存一个临时数据。每个传递加载前两个数据项。然后将较低的保存回文件,并保留较高的。继续逐个加载并保存较低的。最后保存更高的。

不需要随机访问数据,但您确实需要能够随意传递它。