使用指针按字母顺序排列字符串数组

问题描述 投票:0回答:2

我有一个项目,我必须在其中创建一个程序,该程序将允许用户以任何顺序输入名称。然后程序将按字母顺序显示名称。同样,所有这些都必须使用指针来完成。现在,我在程序中的尝试提示用户输入名称并显示名称,但是由于某种原因我无法对其进行排序。有人可以帮我吗?

这是我尝试该程序的时间:

#include <stdlib.h>
#include <stdio.h>
#include <string.h>

int main() {
  int list;
  char *names[20];
  char str[20];
  printf("Enter the number of names: ");
  scanf("%d", &list);
  fflush(stdin);
  for (int i = 0; i < list; i++) {
    printf("Enter name %d: ", i + 1);
    // gets(str);
    scanf("%[^\t\n]s", str);
    fflush(stdin);
    names[i] = (char *)malloc(strlen(str) + 1);
    strcpy(names[i], str);
  }
  void sortNames();
  for (int i = 0; i < 5; i++)
    printf("%s\n", names[i]);
  return 0;
}

void sortNames(char **name, int *n) {
  int i, j;
  for (j = 0; j < *n - 1; j++) {
    for (i = 0; i < *n - 1; i++) {
      if (compareStr(name[i], name[i + 1]) > 0) {
        char *t = name[i];
        name[i] = name[i + 1];
        name[i + 1] = t;
      }
    }
  }
}

int compareStr(char *str1, char *str2) {
  while (*str1 == *str2) {
    if (*str1 == '\0' || *str2 == '\0')
      break;

    str1++;
    str2++;
  }
  if (*str1 == '\0' && *str2 == '\0')
    return 0;
  else
    return -1;
}
c sorting pointers string-comparison
2个回答
1
投票

仅关注排序问题,主要是您永远不会调用以后定义的排序函数。行

void sortNames();

仅用于declare具有标识符sortNames的函数,该函数接受任意数量的任何类型的参数(可能不完全是您想做的事情)。我建议将这一行修改为

sortNames(names, list); // Not &list because I'm about to suggest not taking it as a pointer

然后是sortNames函数本身,我不清楚您为什么将数组的长度作为指针进行排序,而不是仅仅传递int本身。我建议将此功能修改为

void sortNames(char **name, int n) {
  int i, j;
  for (j = 0; j < n - 1; j++) {
    for (i = 0; i < n - 1; i++) {
      if (compareStr(name[i], name[i + 1]) > 0) {
        char *t = name[i];
        name[i] = name[i + 1];
        name[i + 1] = t;
      }
    }
  }
}

尽管与此相关的一个问题是表达式compareStr(name[i], name[i + 1]) > 0始终为false。这是因为compareStr仅返回0或-1。您可以通过重写compareStr来解决此问题,以正确处理*str1 > *str2的情况。一种可能的方法是

int compareStr(char *str1, char *str2) {
    if (*str1 == '\0' && *str2 == '\0') {
        return 0;
    } else if (*str1 > *str2) {
        return 1;
    } else if (*str1 < *str2) {
        return -1;
    }
    return compareStr(str1 + 1, str2 + 1);
}

尽管您是为了学习而写的,但我建议您尝试修改当前的迭代解决方案,而不仅仅是复制和粘贴此版本。

最后,因为要在定义它们之前使用这些函数,所以您应该在使用它们之前先将它们的定义移动(即先具有compareStr,然后是sortNames,然后是main),或者提供这些功能在文件开头的前向声明,即add

void sortNames(char **name, int n);
int compareStr(char *str1, char *str2);

main之上。


正如其他人指出的那样,您可能希望避免将fflush(stdin)作为其未定义的行为,因此我建议您反对casting the result of malloc


1
投票

这里的问题是函数malloc永远不会返回大于0的值。它只是告诉您两个字符串是否相似。

为了进行排序,您需要添加如下额外的逻辑:

compareStr

此外,您必须以sortNames(names,&list)]的身份调用函数int compareStr(char *str1, char *str2) { while (*str1 == *str2) { if (*str1 == '\0' || *str2 == '\0') break; str1++; str2++; } if (*str1 == '\0' && *str2 == '\0'){ return 0; } else if(*str1 > *str2){ return 1; }else{ return -1; } } ,并确保以正确的顺序编写函数定义或使用函数声明。

© www.soinside.com 2019 - 2024. All rights reserved.