[CSP-S模拟测试]:周(week)(搜索)

题目描述

退役之后,$liu\_runda$总会想起学$OI$的时候自己怎样被郭神虐爆……
$liu\_runda$学文化课的时候想要学$OI$,学$OI$的时候想要学文化课。为了解决矛盾,他决定以周为单位安排文化课和$OI$的学习。例如:学$1$周文化课,学$1$周$OI$,学$1$周文化课,学$2$周$OI$,学$2$周文化课……
距离他退役还有$N$周。他想合理安排这$N$周的学习内容使得自己的知识水平在$N$周之后尽量高。一个人的$OI$水平$LevelOI$和文化课水平$LevelWHK$的乘积等于知识水平$LevelZS$。具体来说,$LevelOI$和$LevelWHK$都是一个整数,而$LevelZS=LevelOI\times LevelWHK$。
在这$N$周之前,$liu\_runda$太颓了,故一开始他的$OI$水平为$0$,文化课水平为$0$。在第$i$周,如果他学习文化课,他的文化课水平提高$a_i$,$OI$水平降低$b_i$;如果他学习$OI$,他的$OI$水平提高$c_i$,文化课水平降低$d_i$。$OI$水平和文化课水平的最大值没有限制,但最低不会小于$0$。即,如果$OI$水平/文化课水平不足$x$的时候减少了$x$,那么将变为$0$而不是一个负数。
$liu\_runda$现在实在是太咸鱼了,求不出他能够达到的最高知识水平,于是造了个题出到联考里,要选手求出他能够达到的最高的知识水平$LevelZS$。


输入格式

第一行一个整数$N$。
接下来$N$行每行$4$个空格隔开的整数$a_i,b_i,c_i,d_i$。


输出格式

一行一个整数表示答案。


样例

样例输入

2
666 233 666 233
666 233 666 233

样例输出

288378


数据范围与提示

前$4$个测试点满足:对于第$i$个测试点,$N=i$。
第$5$个测试点满足:所有$b_i=0$,所有$d_i=0$,所有$a_i=1$,所有$c_i=1$。
第$6$个测试点满足:所有$b_i=1$,所有$d_i=1$,所有$a_i=0$,所有$c_i=0$。
全部数据,$1\leqslant N\leqslant 15,0\leqslant a_i,b_i,c_i,d_i\leqslant 1,000,000$。


题解

本身这道题这么简单,我都不想写题解了,但是作为我$AK$的第一套题的$T1$,我还是简单说一下吧。

题很简单,爆搜没什么说的,刚学一个月都能做出来。

但是考场上$56$个人还是有$9$个人没有$A$掉,甚为可惜。

发现其中有好多人选择了状压$DP$,然后没打对,有些人看错了$a,b,c,d$的顺序,有些人没有开$long\ long$,总之无非就是两种人:

  一种是把题想复杂的,这种情况一定要避免,想当年袁神$NOIPD1T1$200多行树套树直接心态炸裂,惨痛退役,在此惊醒各位一定不要做这种人,这样是最亏的,比别人努力,但是却不如别人收获的多。

  另一种则是把这道题想的太简单,根本就不去检查,这种情况也要避免,举个最简单的例子,日军侵华就是低估了中国人民的实力,我在考场上认真读了三遍这道题,就是为了确保细节,说实话我都觉得自己有点偏向第一种人了。

话不多说了。

时间复杂度:$\Theta(2^n)$。

期望得分:$100$分。

实际得分:$100$分。


代码时刻

#include<bits/stdc++.h>
using namespace std;
int n;
long long a[20],b[20],c[20],d[20];
long long ans;
void dfs(int x,long long w,long long o)
{
	if(x>n)
	{
		ans=max(ans,w*o);
		return;
	}
	dfs(x+1,w+a[x],max(o-b[x],0LL));
	dfs(x+1,max(w-d[x],0LL),o+c[x]);
}
int main()
{
	scanf("%d",&n);
	for(int i=1;i<=n;i++)
		scanf("%lld%lld%lld%lld",&a[i],&b[i],&c[i],&d[i]);
	dfs(1,0,0);
	cout<<ans<<endl;
	return 0;
}

rp++

posted @ 2019-08-14 21:10  HEOI-动动  阅读(181)  评论(0编辑  收藏  举报