输入包括一行,包含两个整数n和k(k < n ≤ 1000)
输出满足条件的排列数,答案对2017取模。
5 2
66
// 按照赞最多的实现的dp
import java.util.Scanner;
public class Main{
public static void main(String[] args){
Scanner sc = new Scanner(System.in);
while(sc.hasNext()){
int n = sc.nextInt();
int k = sc.nextInt();
int[][] dp = new int[n+1][k+1];
for(int i=0;i<=n;i++)dp[i][0] = 1;
for(int i=2;i<n+1;i++){
for(int j=1;j<=k && j<i;j++){
if(j==i-1)dp[i][j]=1;
else if(i>j-1){
dp[i][j] = (dp[i-1][j-1]*(i-j) + dp[i-1][j]*(j+1))%2017;
}
}
}
System.out.println(dp[n][k]);
}
}
} //根据最高赞答案,写的java代码,感谢!
import java.util.Scanner;
public class Main{
static int dp[][];
public static void main(String[] args){
Scanner in = new Scanner(System.in);
int n = in.nextInt();
int k = in.nextInt();
dp = new int[n][k+1];
for(int i = 1;i<n;i++){
dp[i][0] = 1;
}
System.out.print(permutationAmount(n,k));
}
public static int permutationAmount(int n ,int k){
if(n == 2 && k == 0){
dp[n-1][k] = 1;
return dp[n-1][k];
}
if(n == 2 && k == 1){
dp[n-1][k] = 1;
return dp[n-1][k];
}
if(n<=k)
return 0;
if(dp[n-1][k] != 0)
return dp[n-1][k];
dp[n-1][k] = (permutationAmount(n-1,k-1)*(n-k)+permutationAmount(n-1,k)*(k+1))%2017;
return dp[n-1][k];
}
}
//很直观的dp,dp[i][j]是前i个数小于符号为j个时的排列个数importjava.util.*;publicclassMain {publicstaticvoidmain(String[] args){Scanner in=newScanner(System.in);intn=in.nextInt();intk=in.nextInt();int[][] dp=newint[n][k+1];intmod=2017;dp[1][0]=1;dp[1][1]=1;for(inti=2;i<n;++i){for(intj=0;j<=Math.min(k, i);++j){if(j==0){dp[i][j]=dp[i-1][0];continue;}dp[i][j]=(dp[i-1][j]*(j+1)+dp[i-1][j-1]*(i-j+1))%mod;}}System.out.println(dp[n-1][k]);in.close();}}
#include <iostream>using namespace std;intmain() {intn, k;cin >> n >> k;int**dp = newint*[n + 1]();for(inti = 0; i < n + 1; ++i)dp[i] = newint[i]();for(inti = 1; i < n + 1; ++i)dp[i][0] = dp[i][i - 1] = 1;for(inti = 3; i < n + 1; ++i)for(intj = 1; j < i - 1; ++j)dp[i][j] = (dp[i - 1][j - 1] * (i - j) + dp[i - 1][j] * (j + 1)) % 2017;cout << dp[n][k] << endl;for(inti = 0; i < n + 1; ++i)delete[] dp[i];delete[] dp;return0;}
遇事不决先打表
1
1 1
1 4 1
1 11 11 1
1 26 66 26 1
1 57 302 302 57 1
1 120 1191 2416 1191 120 1
然后找规律->AC
#include<iostream>
#include<algorithm>
#include<cstring>
#include<map>
#include<bits/stdc++.h>
using namespace std;
int z[1005];
int a[1005];
int main()
{
int n;
cin>>n;
for(int i=0;i<n;i++){
z[i]=i;
}
do{
int sum=0;
for(int i=0;i<n;i++){
if(z[i]<z[i+1]) sum++;
}
a[sum]++;
}while(next_permutation(z,z+n));
for(int i=0;i<n;i++) {
cout<<i<<' '<<a[i]<<endl;
}
return 0;
}
#include<iostream>
#include<algorithm>
#include<cstring>
#include<map>
#include<bits/stdc++.h>
using namespace std;
int z[1005][1005];
int a[1005];
int main()
{
// freopen("in","r",stdin);
for(int i=0;i<1005;i++) z[i][i-1]=z[i][0]=1;
for(int i=2;i<1005;i++){
for(int j=1;j<i;j++){
z[i][j]=(j+1)*z[i-1][j]+(i-j)*z[i-1][j-1];
z[i][j]%=2017;
}
}
int n,k;
cin>>n>>k;
cout<<z[n][k]<<endl;
return 0;
}
package main
import "fmt"
func main() {
var n, k int
fmt.Scan(&n, &k)
dp := make([][]int, n+1)
for i := 0; i < len(dp); i++ {
dp[i] = make([]int, k+1)
}
for i := 0; i <= n; i++ {
dp[i][0] = 1
}
for i := 2; i < n+1; i++ {
for j := 1; j <= k && j < i; j++ {
if j == i-1 {
dp[i][j] = 1
} else if i > j-1 {
dp[i][j] = (dp[i-1][j-1]*(i-j) + dp[i-1][j]*(j+1))%2017
}
}
}
fmt.Println(dp[n][k])
} #include<iostream>
#include<algorithm>
#include<vector>
#include<string>
#include<cmath>
#include<iomanip>
using namespace std;
int main()
{
int n, k;
cin >> n >> k;
vector<int> dp(n, 0);
dp[0] = dp[1] = 1;
//cout<<setw(3)<< 1 << ' ' << setw(3) << 1 << ' '<< setw(3) << 0 << ' ' << setw(3) << 0 << ' ' << setw(3) << 0 << endl;
for (int i = 3; i <= n; i++)
{
for (int j = i - 1; j >= 0; j--)
{
if (j != 0) dp[j] = ((i - j) * dp[j - 1] + (j + 1) * dp[j])%2017;
else dp[j] = ((j + 1) * dp[j])%2017;
}
//for (int j = 0; j < n; j++) cout << setw(3)<< dp[j] << ' ';
//cout << endl;
}
cout << dp[k];
} 用c语言来实现
#include <stdio.h>
#include <stdlib.h>
int d[1005][1005];
int main()
{
int n,k;
int i,j;
while(scanf("%d %d",&n,&k)!=EOF)
{
for(i=1;i<=n;i++)
for(j=0;j<=k;j++)
d[i][j]=0;
for(i=1;i<=n;i++)
{
d[i][0]=1;
}
for(i=2;i<=n;i++)
{
for(j=1;j<=k;j++)
{
d[i][j]=d[i-1][j-1]+d[i-1][j]+d[i-1][j]*j+d[i-1][j-1]*(i-j-1);
d[i][j]=d[i][j]%2017;
}
}
printf("%d\n",d[n][k]);
}
return 0;
}
#include<iostream>
#include<string.h>
using namespace std;
int main()
{
int n, k;
cin>>n>>k;
int dp[n+1][n];
memset(dp,0,sizeof(dp));
dp[1][0]=1;
for(int i=2; i<=n; ++i)
for(int j=0; j<n; ++j)
{
if(j==0)
dp[i][j]=1;
else
dp[i][j]=(dp[i-1][j]*(j+1)+dp[i-1][j-1]*(i-j))%2017;
}
cout<<dp[n][k]<<endl;
return 0;
}
import java.util.Scanner;
/*
*
* 参考大神的解题思路:https://www.nowcoder.com/test/question/done?tid=14939450&qid=95828#summary
* 使用动态规划,真的难想,话说只有动态规划才适合此题
*
* dp[i][j] 表示i个序列有j个'<',对于i+1个序列,可以进行如下分析
* 1.直接添加到最开始,此时多添加一个>,种类数+dp[i-1][j];
* 2.直接添加到最后面,此时多添加一个<,种类数+dp[i-1][j-1];
* 3.添加到中间任意一个<,例如1<2,变成1<3>2,多添加了一个>,种类数+dp[i-1][j]*j;
* 4.添加到中间任意一个>,例如2>1,变成2<3>1,多添加了一个<,种类数+dp[i-1][j-1]*(i-j-1)
* 整理可得到:dp[i][j] = dp[i-1][j]*(j+1)+dp[i-1][j-1]*(i-j)
*
* */
public class Inequtation {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
while (scanner.hasNext()) {
int n = scanner.nextInt();
int k = scanner.nextInt();
int[][] dp = new int[n + 1][k + 1];
for (int i = 1; i <= n; i++) {
dp[i][0] = 1;
}
for (int i = 2; i <= n; i++) {
for (int j = 1; j <= k; j++) {
dp[i][j] = (dp[i - 1][j] * (j + 1) + dp[i - 1][j - 1] * (i - j)) % 2017;
}
}
System.out.println(dp[n][k]);
}
}
}
#include <stdio.h>
int main() {
int n, k;
scanf("%d%d", &n, &k);
long long dp[1001][1001] = {0};
for (int i = 1; i <= n; ++i) {
for (int j = 0; j <= (i % 2 == 0 ? i >> 1 - 1 : i >> 1); ++j) {
if (j == 0) {
dp[i][j] = 1;
}
else if (j == 1) {
dp[i][j] = (dp[i - 1][j] * 2 + i - 1) % 2017;
}
else {
dp[i][j] = (dp[i - 1][j - 1] * (i - j) + dp[i - 1][j] * (j + 1)) % 2017;
}
dp[i][i - j - 1] = dp[i][j];
}
}
printf("%lld\n", dp[n][k] % 2017);
return 0;
}
package BaiduCorrect;
import java.util.Scanner;
public class test5 {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
int n = scanner.nextInt();
int k = scanner.nextInt();
int [] [] dp = new int[1001][1001];
dp[1][0] = 1;
for(int i = 2;i <= n;i++){
for(int j = 0;j < n;j++){
if(j == 0){
dp[i][j] = 1;
}
else {
dp[i][j]=(dp[i-1][j-1]*(i-j)+dp[i-1][j]*(j+1))%2017;
}
}
}
System.out.println(dp[n][k] % 2017);
}
}
var ins = readline().split(" ");
var n = parseInt(ins[0]);
var num = parseInt(ins[1]);
function numbers(total, k){
var arr = [];
for(var i=0; i<total+1; i++){
arr[i] = [];
arr[i][0] = 1;
}
for(var j=0; j<k+1; j++){
arr[0][j] = 0;
}
for(var n=1; n<total+1; n++){
for(var m=1; m<k+1; m++){
arr[n][m] = (arr[n-1][m-1]*(n-m) + arr[n-1][m]*(m+1))%2017;
}
}
return arr[total][k];
}
print(numbers(n, num));