输入一个数,打印从 1 ~ n 的全排列(C语言 字典序法)

字典序法实现全排列

  1. 算法思想在permutation( ) 函数中体现
  1. 代码要求:
    输入一个数,将从 1 ~ n 的全排列打印出

A. 字典序算法思想:

  1. 从右往左, 找到第一个右邻大于自己的数Array[a]
  2. 从右往左, 找出第一个大于Array[a]的数,记为Array[b]
  3. 交换Array[a]和Array[b]
  4. 交换前Array[a]下标 “后面的” 数据由小往大排列

B. 例:输入5

在这里插入图片描述

C. 具体代码

#include <stdio.h>
void permutation(int n);/*排列过程,important!!!*/ 
void creatArray(int array[], int n);/*创建从 1 到 n 的数组*/ 
int  calculate(int n);/*计算所有的排列方式*/ 
void print(int array[], int n);/*打印数组数据*/ 
int  getArray_A(int array[], int n);/*获取Array[a]的下标*/ 
int  getArray_B(int array[], int array_a, int n);/*获取Array[b]的下标*/ 
void swap(int *a, int *b);/*交换数组中的两个数,用于交换Array[a],Array[b]*/
void sort(int array[], int start, int end);/*排序函数,用于每次循环的Array[a]后数组数据的排序*/ 


int main(void)
{
	int n; 
	printf("Please input a number:");
	scanf("%d", &n);
	permutation(n); /*这个英文单词意思是排列,英语没学好,查字典的*/ 
	return 0;
}


/*排列过程,important!!!*/ 
void permutation(int n){
	int Array[n];		/*从一到 n 的数组*/ 
	int num_permutation;/*接收组合数个数*/ 	 
	int Array_A,Array_B;/*接收获得需要交换值的下标*/ 
	
	creatArray(Array, n);						/*1. 创建一个从一到 n 的数组*/
	
	num_permutation = calculate(n);				/*2. 计算组合数个数*/ 
	
	for(int i=0; i<num_permutation; i++){		/* 3. 进入循环*/ 
		print(Array, n);							/*a. 打印排列好的数组*/ 
		
		Array_A = getArray_A(Array, n);				/*b. 获取Array[a]的下标:从右往左,找到第一个右邻大于自己的数*/ 
		
		Array_B = getArray_B(Array, Array_A, n);	/*c. 获取Array[b]的下标:从右往左,找出第一个大于Array[a]的数*/
		
		swap(Array+Array_A, Array+Array_B);			/*d. 交换Array[a]和Array[b]*/ 
		
		sort(Array, Array_A+1, n);					/*e. 将Array[a] "后面的" 数据由小往大排列*/ 
	} 
}




/*创建从 1 到 n 的数组*/ 
void creatArray(int array[], int n){
	for(int i=0; i<n; i++){
		array[i] = i+1;
	}
	return array;
}
/*计算所有的排列方式*/ 
int calculate(int n){
	int num = 1;
	for(int i=1; i<=n; i++){
		num *= i;
	}
	return num;
}
/*打印数组数据*/ 
void print(int array[], int n){
	for(int i=0; i<n; i++){
		printf("%d", array[i]);
	}
	printf("\n");
}
/*获取Array[a]的下标*/ 
int getArray_A(int array[], int n){
	for(int i=n; i>0; i--){
		if(array[i-1] < array[i]){
			return i-1;
		}			
	}
}
/*获取Array[b]的下标*/ 
int getArray_B(int array[], int array_A, int n){
	for(int i=n; i>0; i--){
		if(array[i] > array[array_A]){
			return i;
		}
	} 
}
/*交换数组中的两个数,用于交换Array[a],Array[b]*/ 
void swap(int *a, int *b){
	int temp = *a;
	*a = *b;
	*b = temp;
}
/*排序函数,用于每次循环的Array[a]后数组数据的排序*/ 
void sort(int array[], int start, int end){
	for(int i=0; i<end-start-1; i++){
		for(int k=start; k<end-i-1; k++){
			if(array[k] > array[k+1]){
				int temp = array[k];
				array[k] = array[k+1];
				array[k+1] = temp;
			}
		}
	}
}

发布了108 篇原创文章 · 获赞 114 · 访问量 8557

猜你喜欢

转载自blog.csdn.net/weixin_45773503/article/details/104732087