目录

花店橱窗

目录

dp[i][j]表示摆了i种花,且第i种花的位置在j的最大值,location[i][j]表示第i种花摆在j时上一种花摆在哪。

1.因为可能有负数,所以dp要初始化为负无穷,dp[0][0] = 0为边界

2.第i种花的位置必须要大于第i-1种花,所以j的范围要注意,要从i-1开始,到m-(n-i)结束

3.第三个循环的k表示上一种花的位置,这里k要升序循环,因为答案要求按照字典序

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
#include<iostream>
#include<cstring>
using namespace std;
long long dp[201][201], location[201][201], a[201][201];//no i flower @ j
long long n, m;

void print(long long num, long long x)
{
	if(num == 1)
		cout << x << " ";
	else
	{
		print(num - 1, location[num][x]);
		cout << x << " ";
	}
}

int main()

{
	memset(dp, 128, sizeof(dp));
	long long ans = -214748364;
	cin >> n >> m;
	for(long long i = 1; i <= n; i++)
	{
		for(long long j = 1; j <= m; j++)
		{
			cin >> a[i][j];
		}
	}
	dp[0][0] = 0;
	for(long long i = 1; i <= n; i++)
	{
		for(long long j = i; j <= m - (n - i); j++)
		{
			for(long long k = i - 1; k <= j - 1; k++)
				if(dp[i - 1][k] + a[i][j] > dp[i][j])
				{
					dp[i][j] = dp[i - 1][k] + a[i][j];
					location[i][j] = k;
				}
		}
	}
	long long x;
	for(long long i = n; i <= m; i++)
	{
		if(dp[n][i] > ans)
		{
			ans = dp[n][i];
			x = i;
		}
	}
	cout << ans << endl;
	print(n, x);
	return 0;
}