题意:一个数组s,再给你a,b值,除了s1和sn外,你可以攻击其他元素,你对这个元素的伤害为a,那么他两边的元素会受到b的牵连伤害,si-a,si-1-b,si+1-b;
求最小的次数,使得这个数组的值全部小于0;
解题思路:首先1和n不能直接攻击,所以我们得先把1和n的先处理下,然后我们会发现剩下的元素都有两种状态,一种是我们直接打死他,另一种是我们通过牵连伤害打死他,因为数据小,所以直接暴力搜索就行了
代码:
#include<iostream>
#include<algorithm>#include<cstring>#include<cstdio>#include<cmath>#include<cstdlib>#include<set>#include<map>#include<queue>#include<vector>#define ll long long int#define mod 1000000007#define me(a,b) memset(a,b,sizeof(a))const int inf=0x7fffffff;using namespace std;int h[20];int ans=inf;int n,a,b;void dfs(int pos,int sum){ if(pos==n) { ans=min(ans,sum); return; } if(h[pos-1]<0) dfs(pos+1,sum); int v=0; if(h[pos-1]>=0) { v=h[pos-1]/b+1; h[pos-1]-=v*b; h[pos]-=v*a; h[pos+1]-=v*b; dfs(pos+1,sum+v); h[pos-1]+=v*b; h[pos]+=v*a; h[pos+1]+=v*b; } int vv=h[pos]/a+1; if(h[pos]>=0&&vv>v) { for(int i=v+1;i<=vv;i++) { h[pos-1]-=i*b; h[pos]-=i*a; h[pos+1]-=i*b; dfs(pos+1,sum+i); h[pos-1]+=i*b; h[pos]+=a*i; h[pos+1]+=b*i; } } return;}int main(){ int h1,hn; while(cin>>n>>a>>b) { h1=0; hn=0; for(int i=1;i<=n;i++) cin>>h[i]; h1=h[1]/b+1; h[1]=h[1]-h1*b; h[2]=h[2]-h1*a; h[3]=h[3]-h1*b; if(h[n]>=0) { hn=h[n]/b+1; h[n]=h[n]-hn*b; h[n-1]=h[n-1]-hn*a; h[n-2]=h[n-2]-hn*b; } dfs(2,0); cout<<ans+h1+hn<<endl; } return 0;}