如何按1长度和2字母顺序对char数组进行排序?

问题描述

我正在学习C编程并从事学校作业。可以问老师或同伴的可能性有限(由于电晕爆发和在家疏远),我正在与您联系。非常感谢您的帮助。

我的挑战:编写一个程序,该程序使用不同的功能来对11个文本字符串进行排序,这些字符串的长度和字母顺序有关。告诉用户程序的限制是什么。

Desired output,for instance:
bc
bcb
bcebc
cbbcac
dbccac
(...)

首先,用户必须输入11个文本字符串。我已经用以下代码解决了这个问题:

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

#define NUMBER_OF_STRINGS 11


int main (void)

char textstrings[NUMBER_OF_STRINGS][15];
int i;

(...) 

printf("Enter 11 textstrings,one by one:\n");
for(i=0;i<NUMBER_OF_STRINGS-1;i++)
   {
   printf("Enter string %d: ",i + 1);
   gets(textstrings[i]);
   }

现在,我们将字符串放入“ textstrings [i]”中,必须对其进行排序和打印。我认为最美观的方式是为每个排序条件都具有单独的功能。例如。一个单独的函数用于“长度”,然后另一个用于“字母顺序”。我知道我应该使用“ strlen”比较长度,并使用“ strcmp”比较字母顺序。

我还了解到,按多个条件排序的策略是为每个条件编写比较表达式,这些条件表达式返回比较函数的适当返回类型,并按所需的排序顺序(例如:首先是长度,然后是字母顺序。

这是我迷路的地方...

但是,我确实知道按长度排序的逻辑看起来像这样:

char* temp;
int step
int length=20; //Not allowing text longer than 20 characters.

for(step=0;step<length-1;step++)
for(i=0;i<length-step-1;i++)
  {
  if(strlen(textstrings[i])>strlen(textstrings[i+1]))
   {
   temp=textstrings[i];
   textstrings[i]=textstrings[i+1];
   textstrings[i+1]=temp;
   }

我也了解,按照字母顺序排序可能看起来像这样:

int k,m

for(k=0;k<=NUMBER_OF_STRINGS-1;k++)
{
  for(m=k+1;m<=NUMBER_OF_STRINGS-1;m++)
     if(strmcp(textstrings[k],textstrings[m])>0)
     swap(textstrings[k],textstrings[m]);
}

       where a swap function would look like:

      void swap (char *s1,char *s2)
      {
      char tmp[20];
      strcopy(temp,s1);
      strcopy(s1,s2);
      strcopy(s2,temp);
      }

但是,我不知道如何编写比较表达式,也不了解可以保留在main函数中的哪些代码段以及合适的单独函数一个理想的答案将包括一个示例代码,以显示如何解决此任务,因为我不但迷失了!

谢谢!

解决方法

在C中对数组进行排序时,您的朋友是qsort。您只需实现一个比较功能,然后调用qsort

例如:

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

#define NUMBER_OF_STRINGS 11

int cmplen(const void *p1,const void *p2)
{
    size_t len1 = strlen((const char *) p1);
    size_t len2 = strlen((const char *) p2);
    if (len1 < len2) return -1;
    if (len1 > len2) return  1;
    return 0;
}

int main(int argc,char const *argv[])
{
    char textstrings[NUMBER_OF_STRINGS][15] = {"abcd","dcg","htj","jkler","qwerty","zxcvbnm","a","aa","pppp","lkjh","ld"};
    qsort(textstrings,NUMBER_OF_STRINGS,sizeof textstrings[0],cmplen);
    for (size_t i = 0; i < NUMBER_OF_STRINGS; ++i) puts(textstrings[i]);
    return 0;
}

输出

a
aa
ld
dcg
htj
abcd
pppp
lkjh
jkler
qwerty
zxcvbnm

如果要按长度和长度优先的字母排序,可以将比较功能更改为

int cmplen(const void *p1,const void *p2)
{
    size_t len1 = strlen((const char *) p1);
    size_t len2 = strlen((const char *) p2);
    if (len1 < len2) return -1;
    if (len1 > len2) return  1;
    return strcmp((const char *) p1,(const char *) p2);
}

输出

a
aa
ld
dcg
htj
abcd
lkjh
pppp
jkler
qwerty
zxcvbnm

现在,输出按长度排序,并且按相等的长度将其按字母顺序排序(请注意,与以前的仅按长度排序的代码相比,“ pppp”和“ lkjh”交换了位置)。

顺便说一句:不要使用gets来获取输入。不安全看看fgets