Permutation Sequence

hard math recursion

Problem

Given n and k, return the k-th permutation sequence of the numbers 1..n (1-indexed). Don't generate all n! permutations — derive the answer arithmetically.

Inputn = 3, k = 3
Output"213"
Sorted perms: 123, 132, 213, 231, 312, 321. The 3rd is "213".

def get_permutation(n, k):
    fact = [1] * (n + 1)
    for i in range(1, n + 1): fact[i] = fact[i - 1] * i
    nums = list(range(1, n + 1))
    k -= 1
    out = []
    for i in range(n, 0, -1):
        idx, k = divmod(k, fact[i - 1])
        out.append(str(nums.pop(idx)))
    return "".join(out)
function getPermutation(n, k) {
  const fact = [1];
  for (let i = 1; i <= n; i++) fact.push(fact[i - 1] * i);
  const nums = [];
  for (let i = 1; i <= n; i++) nums.push(i);
  k -= 1;
  let out = "";
  for (let i = n; i >= 1; i--) {
    const idx = Math.floor(k / fact[i - 1]);
    k -= idx * fact[i - 1];
    out += nums.splice(idx, 1)[0];
  }
  return out;
}
class Solution {
    public String getPermutation(int n, int k) {
        int[] fact = new int[n + 1];
        fact[0] = 1;
        for (int i = 1; i <= n; i++) fact[i] = fact[i - 1] * i;
        List<Integer> nums = new ArrayList<>();
        for (int i = 1; i <= n; i++) nums.add(i);
        k -= 1;
        StringBuilder sb = new StringBuilder();
        for (int i = n; i >= 1; i--) {
            int idx = k / fact[i - 1];
            k %= fact[i - 1];
            sb.append(nums.remove(idx));
        }
        return sb.toString();
    }
}
string getPermutation(int n, int k) {
    vector<int> fact(n + 1, 1);
    for (int i = 1; i <= n; i++) fact[i] = fact[i - 1] * i;
    vector<int> nums;
    for (int i = 1; i <= n; i++) nums.push_back(i);
    k -= 1;
    string out;
    for (int i = n; i >= 1; i--) {
        int idx = k / fact[i - 1];
        k %= fact[i - 1];
        out += (char)('0' + nums[idx]);
        nums.erase(nums.begin() + idx);
    }
    return out;
}
Time: O(n²) (linear removal from list) Space: O(n)