js 第n个排列

来源:力扣

给出集合 [1,2,3,…,n],其所有元素共有 n! 种排列。
按大小顺序列出所有排列情况,并一一标记,当 n = 3 时, 所有排列如下:
“123”
“132”
“213”
“231”
“312”
“321”
给定 n 和 k,返回第 k 个排列

以k=3为例,观察数据我们可以分成这样三组数据
(1)“123” “132”
(2)“213” “231”
(3)“312” “321”
我们先确定k在哪一组,显然k应在第二组(3/2向上取整)
再分为两组(已经确定以2开头,此时k = k - 2 * 1 = 1)
(1)“13”
(2)“31”
k/1向上取整得1,要找的在第一组

了解过程以后我们需要寻找规律:(其实就是全排列)

  • 每次分组,分的组数为当前可选数据长度(1,2,3),组内数据的个数,是剩余数据个数的阶乘(2!)
  • 确定k在哪,可以逐层确定它在哪一组,(1) k = 3, k / 2! = 2,在第二组 (2) k = 3 - 1 * 2 = 1, k / 1! = 1, 在第一组

实现代码如下

/**
 * @param {number} n
 * @param {number} k
 * @return {string}
 */
var getPermutation = function(n, k) {
    k -= 1;
    const factorial = new Array(n); //记阶乘的值
    factorial[0] = 1;
    for(let i = 1; i < n; i++){
        factorial[i] =factorial[i-1] * i;
    }
    const nums = [];
    //数位上可取的值
    for(let i = 1; i <= n; i++){
        nums.push(i);
    }
    let res = '';
    for(let i = n - 1; i >= 0; i--){
        let index = Math.floor(k / factorial[i]);   /*确定k在第几组数据*/
        res += nums[index];
        nums.splice(index, 1);
        k -= index * factorial[i];
    }
    return res;
};
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值