给出集合 [1,2,3,…,n],其所有元素共有 n! 种排列。
按大小顺序列出所有排列情况,并一一标记,当 n = 3 时, 所有排列如下:
“123” “132” “213” “231” “312” “321” 给定 n 和 k,返回第 k 个排列。
说明:
给定 n 的范围是 [1, 9]。 给定 k 的范围是[1, n!]。 示例 1:
输入: n = 3, k = 3 输出: “213” 示例 2:
输入: n = 4, k = 9 输出: “2314”
数学
对于n=4,k=9这个数据,可以知道首位是2(
因
为
9
%
3
!
=
3
,
9
/
3
!
=
1
,
所
以
取
1...
n
中
第
2
个
未
被
使
用
过
的
数
字
因为9 \% 3!=3,9/3!=1,所以取1...n中第2个未被使用过的数字
因为9%3!=3,9/3!=1,所以取1...n中第2个未被使用过的数字),之后更新k=3。
下一个数字是第2个未被使用的数字,更新k=1
下一个数字是第1个未被使用的数字,更新k=1
下一个数字是第1个未被使用的数字,更新k=1
循环结束
class Solution {
//当n=i时排列种类
int[] category=new int[]{1,1,2,6,24,120,720,5040,40320,362880};
public String getPermutation(int n, int k) {
String res="";
boolean[] visited=new boolean[n];
int pos=0;
for(int i=n-1;i>=0;i--){
if(k%category[i]!=0){
pos=k/category[i]+1;
k%=category[i];
}else{
//若余数为0,那么k=category[i]
pos=k/category[i];
k=category[i];
}
int j=0,count=0;
//得出第n-i个数字应该是几
for(j=0,count=0;j<n&&count!=pos;j++){
if(!visited[j]){
count++;
}
}
visited[j-1<0?j:j-1]=true;
res+=j;
}
return res;
}
}