今天讲搜索,把深搜和广搜的基础讲了一遍,我理解了它的但我还不会打,应用。so一天我就只打了3题。
第一题:用n个火柴摆加法问能摆多少个等式。
#include<bits/stdc++.h>
using namespace std;
int a[2200]={6,2,5,5,4,5,6,3,7,6};
int main()
{
int n,m,x,l=0;
cin>>n;
for(int i=10;i<=2100;i++)//1~2100中每个数所需的火柴棒
{
x=i;
while(x>0)
{
a[i]=a[i]+a[x%10];
x/=10;
}
}
for(int i=0;i<=1000;i++)//暴力枚举两个加数
for(int j=0;j<=1000;j++)
{
m=i+j;
if(a[i]+a[j]+a[m]+4==n) l++;
}
cout<<l<<endl;
return 0;
}
第二题:有个电梯在第n层,它只能按每一层规定的层数上下走,问能不能到第m层,若能至少要按几次按钮。
#include<bits/stdc++.h>
using namespace std;
int a[210],n,x,y;
long long z=100000000;
bool b[210]={};
void dfs(int now,long long s)//now现在层数,s按按钮次数
{
if(s>z) return ;
if(now==y)
{
z=min(z,s);
return ;
}
if(now+a[now]<=n&&!b[now+a[now]])//是否能上升
{
b[now+a[now]]=1;
dfs(now+a[now],s+1);
b[now+a[now]]=0;
}
if(now-a[now]>0&&!b[now-a[now]])//是否能下降
{
b[now-a[now]]=1;
dfs(now-a[now],s+1);
b[now-a[now]]=0;
}
}
int main()
{
cin>>n>>x>>y;
for(int i=1;i<=n;i++)
cin>>a[i];
dfs(x,0);
if(z!=100000000) cout<<z;
else cout<<"-1";
}
第三题:有头牛使喂给牛的饲料的种数最少,维他命数量又足够。给出牛所需的最低的维他命量,输出喂给牛需要哪些种类的饲料,且所需的饲料剂量最少。dfs深搜模板
#include<bits/stdc++.h>
using namespace std;
int n,m,l=22,z,s=0;
int a[50],b[50][50],c[2100]={},f[22]={},k[22]={};
long long ans1=0,ans2=0;
void dfs(int x,int y)//x表示前x袋饲料要不要已经确定下来,y代表目前要了几袋饲料
{
if(x==m)
{
for(int i=1;i<=n;i++)
if(c[i]<a[i]) return ;
if(y<l)
{
l=y; z=0;
for(int i=1;i<=m;i++)
if(f[i]==1)
k[++z]=i;
return ;
}
if(y==l)
{
ans2=0;
for(int i=1;i<=n;i++)
ans2+=c[i];
if(ans2<ans1)
{
l=y; z=0;
for(int i=1;i<=m;i++)
if(f[i]==1)
k[++z]=i;
}
ans1=ans2;
return ;
}
return ;
}
f[x+1]=1;//要这袋饲料
for(int i=1;i<=n;i++)
c[i]+=b[x+1][i];//c[i]+新加入的量
dfs(x+1,y+1);//搜索
f[x+1]=0;//不要
for(int i=1;i<=n;i++)
c[i]-=b[x+1][i];//回到不要这袋饲料的情况
dfs(x+1,y);
return ;
}
int main()
{
cin>>n;
for(int i=1;i<=n;i++)
cin>>a[i];
cin>>m;
for(int i=1;i<=m;i++)
for(int j=1;j<=n;j++)
cin>>b[i][j];
dfs(0,0);
cout<<l;
for(int i=1;i<=l;i++)
cout<<' '<<k[i];
return 0;
}