待解决

1.紧急抢救

题目描述:

伊莲妮到了岛上发现情况十分危急,每个人的病情各不相同,调查得知岛上有N×M个人,每个人的病情用一个整数K表示,每个月数值增大1,当数值到达一定值Q时就会死亡,所有人的位置大致用一个N×M的矩阵表示,数字表示他们的病情K,如果为0则此处无人;假设小伊(伊莲妮)的家在(sx,sy),她的病情也由其位置的k表示,因为她高尚的品质,她要救完最多能救的所有人才能救自己。她从一个位置可以走向四周四个方向,每一步需要一个月,因为救助很消耗体力,救助一个人她的病情会加剧,她的k加上此人的病情k,因为一路向前是她的信念,所以她不再走回头路,如何保证自己不死亡的情况下救尽量多的人?(不含自己,保证自己生病)

输入输出格式

输入格式:

第一行两个数字n,m分别表示行和列,接下来n+1行每行m个数字用空格隔开为相对位置及位置上的病情,第n+2行为小伊的位置sx,sy和最大上限Q;

输出格式:

输出最多能救的人数p,以及小伊的最后病况k,用一个空格隔开;

输入输出样例

输入样例#1: 复制
5 5
5 7 8 3 1
5 5 7 6 6
6 6 6 2 8
5 7 2 5 8
7 1 0 1 7
1 5 100
#include<iostream>
#include<cstdio>
#include<algorithm>
using namespace std;
int a[11][11];
int vis[11][11];
int n,m,q;
int sx,sy;
int ans,k;
int humen;
int minx=129344124;
int dx[4]={0,0,1,-1},dy[4]={1,-1,0,0};
struct node{
    int minn,x,y;
};node pre;
int add;
void dfs(int sx,int sy,int p,int ph);
int main()
{
    scanf("%d%d",&n,&m);
    for(int i=1;i<=n;i++)
    for(int j=1;j<=m;j++)
    {
        scanf("%d",&a[i][j]);
        if(a[i][j]){
            humen++;
        if(a[i][j]<minx)minx=a[i][j];
        }
    }
    scanf("%d%d%d",&sx,&sy,&q);k=a[sx][sy];vis[sx][sy]=0;
    dfs(sx,sy,0,k);
    printf("%d",ans);
}
void dfs(int sx,int sy,int p,int ph)
{
    if(ph>=q||p==humen-1)
    {
        if(p>ans)ans=p;
        return ;
    }
    else
    {
        if(ans==humen)return ;
        if((q-ph-add-p)/minx+p<ans)return;
        
        node tx;tx.minn=0;
        for(int i=0;i<4;i++)
      {
          int xx=sx+dx[i],yy=sy+dy[i];
          if(xx>=1&&yy>=1&&xx<=n&&yy<=m)
        if(!vis[xx][yy])
        {
        tx.minn=a[xx][yy],tx.x=xx,tx.y=yy;
        if(a[xx][yy])
         {
         add++;
          //cout<<tx.x<<" "<<tx.y<<endl;
           vis[tx.x][tx.y]=1;
          if(a[tx.x][tx.y]+add<q)
          dfs(tx.x,tx.y,p+1,ph+tx.minn+1+add);
          else
          dfs(tx.x,tx.y,p,ph+1);
          vis[tx.x][tx.y]=0;
           add--;
         }   
        }
      }
 

猜你喜欢

转载自blog.csdn.net/k42946/article/details/80738419