UESTC_Just a Maze CDOJ 1162

Just a Maze

Time Limit: 3000/1000MS (Java/Others)     Memory Limit: 262144/262144KB (Java/Others)

Submit Status

Here is a maze with N × M room.

You start from the room (SR,SC) and want to go to the room located at (TR,TC). However, there are many traps and monsters in this maze.

There are 4 types of rooms:

1. Blank->(‘.‘). which has nothing.
2. Rock->(‘#‘). which you can not enter it.
3. Trap->(‘a‘~‘z‘), which once you enter it, you will suffer (Trap-‘a‘+1) damage(s). After you leave,the trap will reset so it can be triggered next time.
4. Monster->(‘A‘~‘Z‘). If you go into a monster room or any room adjacent to a monster room, the monster will immediately rush up to you and fight with you. You will kill it, but you will get hurt too, suffering (Monster-‘A‘+1) damage(s). And the monster will not revive.

Two rooms are adjacent if and only if they share an edge. You can take 1 step to go from a room to another adjacent room.

The safest path is a lowest total damage path. Among all safest path,find the path with lowest steps.

Input

The first line contains two integers N and M (1≤N,M≤500).

The second line contains 4 integers SR,SC,TR,TC (1≤SR,TR≤N and 1≤SC,TC≤M).

For the next N lines, each line contains M characters indicating the map of maze. Each type of room is marked as:

1. Blank->(‘.‘)
2. Rock->(‘#‘)
3. Trap: from ‘a‘~‘z‘
4. Monster: from ‘A‘~‘Z‘

The damage you suffer from the trap ‘a‘ is 1,‘b‘ is 2..and so on.

The damage you suffer from the monster ‘A‘ is 1... and ‘Z‘ is 26.

The room (SR,SC) and (TR,TC) are always blank rooms and will not be adjacent to any monster room.

Output

Output the lowest total damage and the lowest steps in all safest path.

Sample input and output

Sample Input Sample Output
3 5
1 1 3 5
..b..
.zC#.
..a..
4 6

Source

2015 UESTC ACM Summer Training Team Selection (4)

解题报告:

本题的难点在于如何建图,普通简图的话会受到多次伤害(就是怪物不死的问题)

因为有个条件是怪物不相邻,那么我们就给怪物所在的附近的 4 个格子全部建边(每个格子可以通往另外3个格子),同时我们知道这个时间代价是 2

处理好这个之后,我们考虑如何处理伤害的问题

我们定义Damge( i , j ) 表示从格子i 到 格子j所受的伤害(这个移动只能是相邻的或者通过上面建的边)

Damage(i ,j ) = Damge(j) - ( i , j )之间共享的怪兽的伤害

然后本题就完了

注意不要使用spfa,不要使用spfa,不要使用spfa,重要的事说三遍

请使用dijkstra的堆优化!!

#include <iostream>
#include <cstring>
#include <cstdio>
#include <algorithm>
#include <cmath>
#include <vector>
#include <stack>
#include <map>
#include <set>
#include <queue>
#define pb push_back
#define show(x) cout << "x is " << x << endl
#define printarray(x,n) for(int i = 0 ; i < n ; ++ i) x == 0 ? cout << x[i] : cout << x[i] << " ";cout << endl
#define input_fast std::ios::sync_with_stdio(false);std::cin.tie(0)
#define local freopen("in.txt","r",stdin)
#define loop(x,st,ed) for(int x = st ; x < ed ; ++ x)
#define blackkey
typedef long long ll;
using namespace std;
const int maxn = 500 + 50;

typedef struct status
{
  int x , y  ;
  status(int x, int y )
   {
      this->x = x, this->y = y ;
   }
};

typedef struct Edge
{
  int x , y , co;
  Edge(int x, int y , int co)
   {
      this->x = x , this->y = y , this->co = co;
   }
};

typedef struct qst
{
  int x , y , d1 , d2;
  friend bool operator < (const qst & a , const qst & b)
   {
         if (a.d1 < b.d1)
          return false;
         else if(a.d1 == b.d1 && a.d2 < b.d2)
          return false;
         return true;
   }
  qst(int x,int y,int d1,int d2)
   {
        this-> x = x , this->y = y , this->d1 = d1 , this->d2 = d2;
   }
};

typedef pair<int,int>pos;
typedef pair<pos,pos>spj;
int n , m , sr , sc , tr , tc , mincost[maxn][maxn][2] , dir[4][2] = {-1,0,1,0,0,1,0,-1} , damage[maxn][maxn] , ban[maxn][maxn] , damage2[maxn][maxn] ,used[maxn][maxn] ;
char s[maxn][maxn];
vector<Edge>E[maxn][maxn];
set<spj>sb;
priority_queue<qst>q;

inline int inmap(int x,int y)
{
   return x <= n && x >= 1 && y <= m && y >= 1;
}

int GetSameDamage(int x1,int y1,int x2,int y2)
{
   int ans = 0;
   loop(i , 0 , 4)
    {
        int newx = x1 + dir[i][0];
        int newy = y1 + dir[i][1];
        if (s[newx][newy] <= ‘Z‘ && s[newx][newy] >= ‘A‘)
         {
             loop(j , 0 , 4)
              if (x2 + dir[j][0] == newx && y2 + dir[j][1] == newy)
               {
                    ans += s[newx][newy] - ‘A‘ + 1;
                    break;
              }
         }
    }
   return ans;
}

void dijkstra()
{
  q.push(qst(sr,sc,0,0));
  memset(mincost,-1,sizeof(mincost));
  mincost[sr][sc][0] = mincost[sr][sc][1] = 0;
  while(!q.empty())
   {
         int x = q.top().x , y = q.top().y , d1 = q.top().d1 , d2 = q.top().d2 ; q.pop();
         if (used[x][y])
          continue;
         used[x][y] = 1;
         loop(i , 0 , 4)
         {
              int newx = x + dir[i][0] , newy = y + dir[i][1] ;
              if (!inmap(newx,newy) || ban[newx][newy]) continue;
             int newhurt = d1 + damage[newx][newy] + damage2[newx][newy] , newcost = d2 + 1;
             if ( newhurt < mincost[newx][newy][0] || !(mincost[newx][newy][0] ^ -1)  )
              {
                   mincost[newx][newy][0] = newhurt;
                   mincost[newx][newy][1] = newcost;
                   q.push(qst(newx,newy,newhurt,newcost));
              }
             else if( !(newhurt ^ mincost[newx][newy][0]) && newcost < mincost[newx][newy][1])
              {
                    mincost[newx][newy][1] = newcost;
                    q.push(qst(newx,newy,newhurt,newcost));
              }
         }
      loop(i , 0 , E[x][y].size() )
         {
              int newx = E[x][y][i].x , newy = E[x][y][i].y , add = E[x][y][i].co;
             int newhurt = d1 + damage[newx][newy] + damage2[newx][newy] -  add, newcost = d2 + 2;
             if ( newhurt < mincost[newx][newy][0] || !(mincost[newx][newy][0] ^ -1) )
              {
                   mincost[newx][newy][0] = newhurt;
                   mincost[newx][newy][1] = newcost;
                   q.push(qst(newx,newy,newhurt,newcost));
              }
             else if( !(newhurt ^ mincost[newx][newy][0]) && newcost < mincost[newx][newy][1])
              {
                    mincost[newx][newy][1] = newcost;
                    q.push(qst(newx,newy,newhurt,newcost));
              }
         }
   }
}

int main(int argc,char *argv[])
{
  //local;
  memset(damage , 0 , sizeof(damage));
  memset(damage2 , 0 , sizeof(damage2));
  memset(used,0,sizeof(used));
  scanf("%d%d%d%d%d%d",&n,&m,&sr,&sc,&tr,&tc);
  loop(i , 1 , n + 1)
   scanf("%s",s[i] + 1);
  loop(i , 1 , n + 1)
   loop(j , 1 , m + 1)
    {
        if (s[i][j] == ‘#‘)
         ban[i][j] = 1;
        else if (s[i][j] <= ‘z‘ && s[i][j] >= ‘a‘)
         damage[i][j] = s[i][j] - ‘a‘ + 1;
        else if(s[i][j] <= ‘Z‘ && s[i][j] >= ‘A‘)
         {
             ban[i][j] = 1;
             loop(k , 0 , 4)
              damage2[i + dir[k][0]][j + dir[k][1]] += s[i][j] - ‘A‘ + 1;
             loop(kx , 0 , 4)
              {
                  int newx = i + dir[kx][0] ;
                 int newy = j + dir[kx][1] ;
                 if (!inmap(newx,newy) || s[newx][newy] == ‘#‘) continue;
                 pos p1(newx,newy);
                 loop(k2 , 0 , 4)
                  {
                     int tx = i + dir[k2][0];
                     int ty = j + dir[k2][1];
                     if ( !inmap(tx,ty) || s[tx][ty] == ‘#‘ || (tx ==newx && ty == newy)) continue;
                     pos p2(tx,ty);
                     spj ju = make_pair(p1,p2);
                     if (!sb.count(ju))
                      {
                          int co = GetSameDamage(newx,newy,tx,ty);
                          E[newx][newy].pb(Edge(tx,ty,co));
                          sb.insert(ju);
                      }

                  }
             }
         }
    }
  dijkstra();
  printf("%d %d\n",mincost[tr][tc][0],mincost[tr][tc][1]);
  return 0;
}
时间: 2025-01-02 20:15:23

UESTC_Just a Maze CDOJ 1162的相关文章

hdu 5094 Maze bfs+状态压缩

Maze Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 100000/100000 K (Java/Others) Total Submission(s): 642    Accepted Submission(s): 229 Problem Description This story happened on the background of Star Trek. Spock, the deputy captain of St

[LeetCode] The Maze III 迷宫之三

There is a ball in a maze with empty spaces and walls. The ball can go through empty spaces by rolling up (u), down (d), left (l) or right (r), but it won't stop rolling until hitting a wall. When the ball stops, it could choose the next direction. T

[LeetCode] The Maze II 迷宫之二

There is a ball in a maze with empty spaces and walls. The ball can go through empty spaces by rolling up, down, left or right, but it won't stop rolling until hitting a wall. When the ball stops, it could choose the next direction. Given the ball's 

CDOJ 1273 God Qing&#39;s circuital law

暴力枚举+idea.做的时候mod写错了,写成了1000000009,找了两个多小时才发现...... a[1],a[2],a[3]....a[N] b[1],b[2],b[3]....b[N] 首先需要枚举b[1]...b[N]与a[1]进行组合. 然后对a[2]...a[N]从小到大排序 对b[1],b[2],b[3]....b[N] 除当前与a[1]组合的以外,剩下的从大到小排序 然后找出每一个a[i]在不破坏a[0]最大值的情况下最大能与哪一个b[i]配对. 然后从第N个人开始往第2个人

Fire Maze(广度优先搜索)

Fire Maze Time Limit: 1000 MS Memory Limit: 32768 K Total Submit: 53(19 users) Total Accepted: 26(17 users) Rating: Special Judge: No Description After escaping from Figo's chase, Severus falls into a N * M maze designed by Figo. At first, Severus is

Uva 705 - Slash Maze

  Slash Maze  By filling a rectangle with slashes (/) and backslashes ( ), you can generate nice little mazes. Here is an example: As you can see, paths in the maze cannot branch, so the whole maze only contains cyclic paths and paths entering somewh

Borg Maze

Description The Borg is an immensely powerful race of enhanced humanoids from the delta quadrant of the galaxy. The Borg collective is the term used to describe the group consciousness of the Borg civilization. Each Borg individual is linked to the c

ZOJ 3420 Double Maze (BFS)

链接 :  http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemCode=3420 普通的BFS 两个图的状态表示成一个状态.记录答案直接用string保存操作. #include <iostream> #include <sstream> #include <cstring> #include <cstdio> #include <vector> #include <stac

数据结构与算法4: 经典问题之迷宫问题(Maze path)

数据结构与算法4: 经典问题之迷宫问题(Maze path) 写在前面 本节实践了教材[1][2]的两种经典迷宫算法.注意体会栈的运用.如果有改进意见请帮助我. 1.迷宫问题直观感受 下面给出迷宫问题的一个直观感受图,引入图只是为了帮助直观理解,这里不涉及OpenGL等其他绘图内容. 下图中棕色代表通道阻塞,白色代表可用通道,红色代表起始位置,绿色代表当前位置,黄色代表出口. (采用C++ 和OpenGL 绘制,目前是2D版本,3D版本有空时再补上) 迷宫1: 迷宫2: 2.迷宫算法 2.1 迷