629 K個逆序對陣列

2021-09-24 11:42:30 字數 1296 閱讀 2536

給出兩個整數 n 和 k,找出所有包含從 1 到 n 的數字,且恰好擁有 k 個逆序對的不同的陣列的個數。

逆序對的定義如下:對於陣列的第i個和第 j個元素,如果滿i < j且 a[i] > a[j],則其為乙個逆序對;否則不是。

由於答案可能很大,只需要返回 答案 mod 109 + 7 的值。

示例 1:

輸入: n = 3, k = 0

輸出: 1

解釋:只有陣列 [1,2,3] 包含了從1到3的整數並且正好擁有 0 個逆序對。

示例 2:

輸入: n = 3, k = 1

輸出: 2

解釋:陣列 [1,3,2] 和 [2,1,3] 都有 1 個逆序對。

說明:n 的範圍是 [1, 1000] 並且 k 的範圍是 [0, 1000]。

網上的** 32ms

class solution 

}else}}

return dp[n][k];

}};

定義dp[n][k]表示從1到n構成的數中含有k個逆序對的個數,則我們可以推導出dp[n][k]和dp[n - 1][i]之間的遞推關係:

如果我們把n放在最後一位,則所有的k個逆序對均來自於前n - 1個數所構成的逆序對,和n無關;

如果我們把n放在倒數第二位,則有1個逆序對和n有關,有k - 1個逆序對來自前n - 1個數所構成的逆序對;

如果我們把n放在第一位,則有n-1個逆序對和n有關,k - (n - 1)個逆序對來自前n - 1個數所構成的逆序對。

所以:dp[n][k] = dp[n-1][k]+dp[n-1][k-1]+dp[n-1][k-2]+…+dp[n-1][k+1-n+1]+dp[n-1][k-n+1]。但問題是 k - (n - 1)有可能為負數,也就是說根據n和k的不同,上面的式子有可能從某個項之後就不合法了,我們這裡先寫出來佔位,從而得到下面兩個式子:

dp[n][k] = dp[n-1][k]+dp[n-1][k-1]+dp[n-1][k-2]+…+dp[n-1][k+1-n+1]+dp[n-1][k-n+1]

dp[n][k+1] = dp[n-1][k+1]+dp[n-1][k]+dp[n-1][k-1]+dp[n-1][k-2]+…+dp[n-1][k+1-n+1]

把上面兩個式子相減可以推導出:dp[n][k+1] = dp[n][k]+dp[n-1][k+1]-dp[n-1][k+1-n]。這樣就可以寫出**了。

當然由於dp[n][k]只和dp[n][x],dp[n-1][x]有關,所以該**還可以進一步將空間複雜度從o(nk)降低到o(k)。時間複雜度是o(nk)。

629 K個逆序對陣列

題目描述 給出兩個整數 n 和 k,找出所有包含從 1 到 n 的數字,且恰好擁有 k 個逆序對的不同的陣列的個數。逆序對的定義如下 對於陣列的第i個和第 j個元素,如果滿i j且 a i a j 則其為乙個逆序對 否則不是。由於答案可能很大,只需要返回 答案 mod 109 7 的值。解題思路 思...

629 K個逆序對陣列

題目描述 給出兩個整數 n 和 k,找出所有包含從 1 到 n 的數字,且恰好擁有 k 個逆序對的不同的陣列的個數。逆序對的定義如下 對於陣列的第i個和第 j個元素,如果滿i j且 a i a j 則其為乙個逆序對 否則不是。由於答案可能很大,只需要返回 答案 mod 109 7 的值。示例 1 輸...

629 K個逆序對陣列

給出兩個整數 n 和 k,找出所有包含從 1 到 n 的數字,且恰好擁有 k 個逆序對的不同的陣列的個數。逆序對的定義如下 對於陣列的第i個和第 j個元素,如果滿i j且 a i a j 則其為乙個逆序對 否則不是。由於答案可能很大,只需要返回 答案 mod 109 7 的值。import j a....