如何修改C语言排列代码以生成字典序字符全排列输出
解决字符串不重复字典序排列问题
问题分析
你需要生成小写字母字符串的所有不重复排列,要求先输出排列总数,再按字典序输出所有排列。原代码存在以下问题:
- 输入未处理换行符,导致长度计算错误且排序包含无效字符
- 递归函数的参数和终止条件有误,导致输出不完整或越界
- 未统计排列总数
- 输出格式不符合要求(缺少换行)
修改后的代码
#include <stdio.h> #include <string.h> // 交换两个字符 void swap(char *a, char *b) { char temp = *a; *a = *b; *b = temp; } // 升序排序字符串(冒泡排序,避免依赖外部头文件) void bubble_sort(char array[], int length) { for (int i = 0; i < length - 1; i++) { for (int j = 0; j < length - i - 1; j++) { if (array[j] > array[j + 1]) { swap(&array[j], &array[j + 1]); } } } } int count = 0; // 统计排列总数 void permutations(char array[], int length, int left) { if (left == length) { printf("%s\n", array); count++; return; } for (int i = left; i < length; i++) { // 跳过重复字符,避免生成重复排列 int is_duplicate = 0; for (int j = left; j < i; j++) { if (array[j] == array[i]) { is_duplicate = 1; break; } } if (!is_duplicate) { swap(&array[left], &array[i]); permutations(array, length, left + 1); swap(&array[left], &array[i]); // 回溯 } } } int main(void) { char input[10] = ""; fgets(input, 9, stdin); // 处理输入中的换行符 size_t str_len = strlen(input); if (str_len > 0 && input[str_len - 1] == '\n') { input[str_len - 1] = '\0'; str_len--; } // 先对字符串升序排序,保证后续排列按字典序生成 bubble_sort(input, str_len); // 生成排列 permutations(input, str_len, 0); // 输出排列总数(注意要放在最后,因为count在递归中统计) printf("%d\n", count); return 0; }
修改说明
- 输入处理:移除
fgets读入的换行符,确保字符串仅包含有效小写字母,长度计算准确。 - 内置排序函数:替换外部依赖的
quicksort为冒泡排序,避免因外部头文件实现问题导致排序错误,保证初始字符串是升序,这是字典序排列的基础。 - 排列计数:添加全局变量
count,在每次生成有效排列时递增,最后输出总数。 - 递归逻辑修正:
- 终止条件改为
left == length,此时整个字符串已完成排列,输出并计数。 - 循环范围改为
i < length,避免数组越界。 - 输出时添加换行符,保证每个排列单独一行。
- 终止条件改为
- 回溯逻辑保留:交换后递归,递归结束后交换回来,确保后续循环的数组状态正确。
示例运行
输入:aab
输出:
aab aba baa 3
内容的提问来源于stack exchange,提问作者Phani P
相关产品推荐
相关产品推荐

