《算法竞赛入门经典》5.32排序与检索-字母重排

  输入一个字典(用******结尾),然后再输入若干单词。每输入一个单词w,你都需要在字典中找出所有可以用w的字母重排后得到的单词,并按照字典序从小到大的顺序在一行中输出(如果不存在,输出:()。输入单词之间用空格或空行隔开,且所有输入单词都由不超过6个小写字母组成。注意,字典中的单词不一定按字典序排列。

 1 #include <stdio.h>
 2 #include <stdlib.h>
 3 #include <string.h>
 4 int n;
 5 char word[2000][10], sorted[2000][10];
 6 //字符比较函数
 7 int cmp_char(const void* _a, const void* _b)
 8 {
 9     char*a = (char*) _a;
10     char*b = (char*) _b;
11     return *a - *b;
12 }
13 
14 //字符串比较函数
15 int cmp_string(const void* _a, const void* _b)
16 {
17     char*a = (char*) _a;
18     char*b = (char*) _b;
19     return strcmp(a, b);
20 }
21 
22 int main()
23 {
24     n = 0;
25     for(; ;)
26     {
27         scanf("%s", word[n]);
28         if(word[n][0] == '*') break;                //遇到结束标志就终止循环
29         n++;
30     }
31     qsort(word, n, sizeof(word[0]), cmp_string);    //给所有单词排序
32     for(int i = 0; i < n; i++)
33     {
34         strcpy(sorted[i], word[i]);
35         qsort(sorted[i], strlen(sorted[i]), sizeof(char), cmp_char);//给每个单词排序
36     }
37     char s[10];
38     while(scanf("%s", s) == 1)                        //持续读到文件结尾
39     {
40         qsort(s, strlen(s), sizeof(char), cmp_char);//给输入单词排序
41         int found = 0;
42         for(int i = 0; i < n; i++)
43             if(strcmp(sorted[i], s) == 0)
44             {
45                 found = 1;
46                 printf("%s", word[i]);                //输出原始单词,而不是排序后的
47             }
48         if(!found) printf(":(");
49         printf("
");
50     }
51     return 0;
52 }
View Code

分析:
1.步骤:
  第一步:首先在读入字典后把所有单词排序(确保字典中单词按字典序排列),结果保存在sorted数组;
  第二步:然后把字典中每个单词排序(避免每次重排);
  第三步:每读入一个单词,把该单词各个字母排序后就和字典中所有的单词直接比较,判断两个单词是否可以通过重排得到;
  第四步:每遇到一个满足条件的单词,则立刻输出其在字典中的原始单词。
2.程序使用了<stdlib.h>中的sqort排序函数,虽然用库函数排序的代码量并不比冒泡排序法小,但速度快得多。

亲爱的读者:如果觉得本文对你有所帮助,请点击推荐,分享给其他人!
原文地址:https://www.cnblogs.com/zhuangwei/p/5313504.html