我正在尝试编写一个程序,用C按字母顺序对数字进行排序。
示例输入:
2 35 6 8 4
示例输出:
8 4 6 35 2
数字应该按照代表它们的单词进行排序,例如:
-1-酮
2个
3个
4个
5个
6个
7个
8个
9 9
我可以使用switch
个案对单个数字进行排序。排序两位或更多位数的最佳方法是什么?
答案 0 :(得分:1)
一种方式,不是最有效的方法是:(会给你提示解决问题,而不是完整的解决方案)
sprintf
将数字转换为字符串并存储在字符串数组中。如果要将数字转换为拼写,请使用this excellent tutorial。 (在谷歌搜索的顶部弹出)struct
。比较功能
static int
cmpstringp(const void *p1, const void *p2)
{
return strcmp(* (char * const *) p1, * (char * const *) p2);
}
答案 1 :(得分:0)
每当您需要按一个或另一个值对相关数据集合进行排序时,您应该考虑struct
。保存各种值的结构(整数的{int
值,char *
和整数的char *
字)可以对它们中的任何一个进行排序,并为您提供相关的方法您的值,无论排序顺序如何。
您的基本挑战是使用每个值填充struct数组,在char *
单词上对整数进行排序,然后根据需要使用它。各种转换都非常简单,(1)将int
转换为char *
等价物(基本上与itoa
相反); (2)使用查找表根据(1)中的每个数字连接您的单词等价物。 (除非你只是觉得它,否则不需要在字数之间留一个空格)
查看以下示例。这只是你想要做的事情的一种方式。如果您有疑问,请告诉我们:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
enum {MAXC = 32, MAXW = 64};
/* struct holding both integer and number strings */
typedef struct bs {
int v;
char buf[MAXC];
char str[MAXW];
} bs;
const char *numbers[] = { "zero", /* string lookup */
"one",
"two",
"three",
"four",
"five",
"six",
"seven",
"eight",
"nine" };
char *l2str (long v, char *str, size_t *l);
static int cmpbsp (const void *p1, const void *p2);
int main (void) {
int array[] = {2, 35, 6, 8, 4};
int i, n = sizeof array/sizeof *array;
bs bufstr[n]; /* array of struct */
size_t len = 0;
memset (bufstr, 0, n * sizeof *bufstr); /* initialize to zero */
for (i = 0; i < n; i++) { /* for each in array */
bufstr[i].v = array[i]; /* fill integer val */
l2str (array[i], bufstr[i].buf, &len); /* convert to str */
char *p = bufstr[i].buf;
for (; *p; p++) /* concatenate number for each digit */
strcat (bufstr[i].str, numbers[*p - '0']);
}
for (i = 0; i < n; i++) /* print original sort order */
printf (" bufstr[%d] v : %2d buf : %2s str : %s\n",
i, bufstr[i].v, bufstr[i].buf, bufstr[i].str);
putchar ('\n');
qsort (bufstr, n, sizeof *bufstr, cmpbsp); /* qsort on str */
for (i = 0; i < n; i++) /* print integers alpha-sorted on numbers */
printf (" bufstr[%d] v : %2d buf : %2s str : %s\n",
i, bufstr[i].v, bufstr[i].buf, bufstr[i].str);
putchar ('\n');
return 0;
}
/** convert long to string reversing digits in place.
* base 10 conversion of long value 'v' to string 'str'
* with string length returned through 'l'. 'd' is a
* pointer to the first digit in 'str' used to reverse
* the order of the digits in 'str' in place.
*/
char *l2str (long v, char *str, size_t *l)
{
if (!str) return NULL;
char *d, *p;
char tmp;
/* initialize pointers & length */
d = p = str;
*l = 0;
/* handle negative */
if (v < 0) {
*p++ = '-';
v = -v;
d++;
}
/* convert to char, terminate */
while (v > 0) {
*p++ = (v % 10) + '0';
v /= 10;
}
*p = 0;
*l = (size_t)(p - str);
/* reverse digits in place */
while (--p > d) {
tmp = *p;
*p-- = *d;
*d++ = tmp;
}
return str;
}
/* simple struct compare based on str */
static int cmpbsp (const void *p1, const void *p2)
{
return strcmp (((bs *)p1)->str, ((bs *)p2)->str);
}
<强>输出强>
原始顺序,然后按字母顺序排序顺序(基于one
,two
,...)如下所示。< / p>
$ ./bin/alphasortintarray
bufstr[0] v : 2 buf : 2 str : two
bufstr[1] v : 35 buf : 35 str : threefive
bufstr[2] v : 6 buf : 6 str : six
bufstr[3] v : 8 buf : 8 str : eight
bufstr[4] v : 4 buf : 4 str : four
bufstr[0] v : 8 buf : 8 str : eight
bufstr[1] v : 4 buf : 4 str : four
bufstr[2] v : 6 buf : 6 str : six
bufstr[3] v : 35 buf : 35 str : threefive
bufstr[4] v : 2 buf : 2 str : two
注意:如评论中所提到的,您可以获得将数字转换为字词的链接,您可以通过添加青少年和数十来改善转化权力(例如thirteen
,thirty
等等。只需要额外的努力。