P1064-DP【绿】

发布时间 2023-11-17 15:57:11作者: Kai-G

好多好多天前写了这道题的50分代码,然后不知道错在哪里反复调没调对。然后这周我极度忙,忙死了,好不容易有一点时间再来审视这道题了,然后我5分钟想明白了一切...
把DP数组定义的那句int DP[100][5000]改成int DP[100][50000]就直接AC了...此前的50代码错的5个点都是WA而不是RE,说明编译器并没有就访问越界而报错,我便下意识的认为数组够用,因此完全没想这回事。
但是,我的DP数组是二维数组,这意味着什么呢?
要知道,二维数组其实是骗小孩玩的,现实是计算机内只有一维数组,二维数组只是伪装成仿佛二维的下标形式,实际上都是下标转换后的一维数组,比如对于a[10][100]来说,a[1][1]实际上指的是*(a+101),而越界的标志是*(a+n)中的n>=10*100
明白了吧!
这意味着如果我访问a[1][200]这种逻辑上越界了的数组变量,由于计算机没有二维数组,采用了一种骗人的方式实现二维数组,而这种处理方式会认为这种逻辑上越界的东西实际上并没有越界。
因此当数据大但没那么大的时候,就会出现越界了但是不RE却WA的情况(该说是因为数据不够强还是因为数据太强了呢,是还是不是,这是个哲学问题(笑))。因此以后要提高警惕,哪怕是WA,也不代表数组没越界,不能因为没RE就不考虑这事,同时数组大小严格用科学计数法来写,不要自己转换成数字,容易落下某个0!
当我一瞬间意识到以上那几段话的时候,我加了那个0,然后提交了代码,在等待评测结果的那2秒钟内我甚至希望自己依旧WA,因为自己AC了就说明此前困扰自己好几天的那个问题竟是因为一个如此弱智的马虎,显得自己好呆啊。结果很不幸,自己AC了(瞧瞧,这是什么话)
我好呆啊...哎...
总之,算了,毕竟AC了一道绿题...还不错吧...

Code

#include <iostream>
#include <cstring>
#include <string>
#include <cstdio>
#include <cstdlib>
#include <algorithm>
#include <stack>
#include <queue>
#include <map>
#include <unordered_map>
#include <cmath>
using namespace std;
#define int long long
int DP[100][50000],lc[5000],rc[5000],v[5000],w[5000],q[5000],P,n,m,np=1;
int dfs(int spe,int mon)
{
	if(DP[spe][mon]!=-1)return DP[spe][mon];
	if(q[spe]!=0)return DP[spe][mon]=dfs(spe-1,mon);
	if(mon==0)return DP[spe][mon]=0;
	if(spe==0)
	{
		return DP[spe][mon]=0;
	}
	int DFS=0;
	DFS=max(DFS,dfs(spe-1,mon));
	if(mon-v[spe]>=0) 
		DFS=max(DFS,dfs(spe-1,mon-v[spe])+w[spe]*v[spe]);
	if(lc[spe]!=-1)
	{
		if(mon-v[spe]-v[lc[spe]]>=0)
			DFS=max(DFS,dfs(spe-1,mon-v[spe]-v[lc[spe]])+w[spe]*v[spe]+w[lc[spe]]*v[lc[spe]]);
		if(rc[spe]!=-1)
		{
			if(mon-v[spe]-v[rc[spe]]>=0)
				DFS=max(DFS,dfs(spe-1,mon-v[spe]-v[rc[spe]])+w[spe]*v[spe]+w[rc[spe]]*v[rc[spe]]);
			if(mon-v[spe]-v[lc[spe]]-v[rc[spe]]>=0)
				DFS=max(DFS,dfs(spe-1,mon-v[spe]-v[lc[spe]]-v[rc[spe]])+w[spe]*v[spe]+w[rc[spe]]*v[rc[spe]]+w[lc[spe]]*v[lc[spe]]);
		}
	}
	return DP[spe][mon]=DFS;
}
signed main()
{
	cin>>n>>m;
	memset(lc,-1,sizeof(lc));
	memset(rc,-1,sizeof(rc));
	memset(DP,-1,sizeof(DP));
	for(int i=1;i<=m;i++)
	{
		cin>>v[i]>>w[i]>>q[i];
		if(q[i]!=0)
		{
			if(lc[q[i]]==-1)lc[q[i]]=i;
			else rc[q[i]]=i;
		}
	}
	cout<<dfs(m,n)<<endl;
	return 0;
}