• BOI 2013 Tracks in the snow Flood-fill


    题目

    BOI 2013
    Rostock, Germany
    April 8 – May 12, 2013 b i Day 2
    ENG
    tracks
    Page 1 of 2
    Tracks in the Snow
    There is a rectangular meadow in a forest, having been covered with a blanket of fresh snow in the
    morning (left in the figure below).
    Rabbits and foxes, who live in the forest, are crossing the meadow and leave their tracks in the snow.
    They always enter in the upper left corner and leave the meadow from the lower right corner. In
    between they can move back and forth, playing in the snow, even crossing their own tracks. At any
    time there is at most one animal on the meadow. No animal enters the meadow more than once. The
    movements of the animals can be described by dividing the meadow into quadratic cells. The animals
    never move diagonally in a single step and they never jump over a cell. When an animal enters a cell
    its tracks will cover all previous tracks left in this cell.
    For example, first a rabbit crossed the meadow from top-left to bottom-right (middle in the figure).
    After that, a fox crossed, and now his tracks are partially covering the rabbit’s (right in the figure).
    ........ RRR..... FFR.....
    ........ ..RRR... .FRRR...
    ........ ..R..... .FFFFF..
    ........ ..RRRR.R ..RRRFFR
    ........ .....RRR .....FFF
    You are given a map of the meadow at some time after indicating for each cell if there are any visible
    tracks and whether they were left by a rabbit or by a fox (right in the figure). You are interested in the
    local wildlife population. Write a program to determine the minimal possible number N of animals
    that must have crossed the meadow to leave the given pattern of tracks in the snow.
    Input
    The first line contains two integers H and W, the height and the width of the map of the meadow. H
    lines follow with exactly W characters on each: the map, where ‘.’ marks untouched snow, ‘R’ a spot
    where a rabbit’s track is the topmost one, and ‘F’ a spot where a fox’s track is the topmost one. There
    is at least one track on the meadow.
    Output
    The output should consist of a single integer: the minimal number N  1 of animals that could have
    left the tracks given in the input.
    Constraints
    1  H;W  4000
    In test cases worth 30 points: N  200 and H;W  500
    BOI 2013
    Rostock, Germany
    April 8 – May 12, 2013 b i Day 2
    ENG
    tracks
    Page 2 of 2
    Example
    Input Output
    5 8
    FFR.....
    .FRRR...
    .FFFFF..
    ..RRRFFR
    .....FFF
    2
    Limits
    Time limit: 2 sec per test case
    Memory limit: 1300 MB per test case

    分析

    首先我们先从简单的地方开始,首先不难判断出最后一次的动物是怎么走的。用属于来说,就是起点和终点所在的联通块。这个概念在这道题里还是比很重要的。然后对于这个联通块进行染色(用一个数字来标记这个联通块里的格子)。

    其实就是先将起点入队,然后用BFS从起点开始向上下左右进行发散,(先判断是否这个点可行)将新点入队。如果新的点与前一个点颜色匹配,那么刷成同一种颜色,如果不是同种颜色,就用没用过的另一种颜色来代替(也就是Track[v.x][v.y] != Track[u.x][u.y]成立的情况下,Anti为1,那么color[v.x][v.y] = color[u.x][u.y]+Anti;就会使得color[v.x][v.y] = color[u.x][u.y]+1)。直到所有的点遍历完成,那么其中最大的数字(最后一个染上的颜色)就是我们要的答案(还要+1啊!)。

    这就是这道题的算法:Flood-fill

    程序

     1 #include <bits/stdc++.h>
     2 using namespace std;
     3 const int MAXN = 4000+1;
     4 const int dx[4] = {1,0,-1,0}, dy[4] = {0,1,0,-1};
     5 char Track[MAXN][MAXN];
     6 bool vis[MAXN][MAXN];
     7 int h, w, color[MAXN][MAXN];
     8 struct node
     9 {
    10     int x,y;
    11 };
    12 void BFS()
    13 {
    14     memset(color,0,sizeof(color));
    15     queue<node> Q[2];
    16     memset(vis,false,sizeof(false));
    17     int Now = 0;
    18     Q[Now].push((node){1,1});
    19     vis[1][1] = true;
    20     while (!Q[Now].empty())
    21     {
    22         while (!Q[Now].empty())
    23         {
    24             node u = Q[Now].front();
    25             Q[Now].pop();
    26             for (int i = 0; i < 4; i++)
    27             {
    28                 node v = (node){u.x+dx[i],u.y+dy[i]};
    29                 if (v.x > h || v.x < 1 || v.y > w || v.y < 1 || Track[v.x][v.y] == '.' || vis[v.x][v.y])
    30                     continue;
    31                 int Anti = (Track[v.x][v.y] != Track[u.x][u.y]);
    32                 vis[v.x][v.y] = true;
    33                 color[v.x][v.y] = color[u.x][u.y]+Anti;
    34                 Q[Now^Anti].push(v);
    35             }
    36         }
    37         Now = 1-Now;
    38     }
    39     int ans = 0;
    40     for (int i = 1; i <= h; i++)
    41         for (int j = 1; j <= w; j++)
    42             ans = max(ans, color[i][j]);
    43     cout << ans+1 << endl;
    44 }
    45 int main()
    46 {
    47     freopen("tracks.in","r",stdin);
    48     freopen("tracks.out","w",stdout);
    49     cin >> h >> w;
    50     for (int i = 1; i <= h; i++)
    51         for (int j = 1; j <= w; j++)
    52             cin >> Track[i][j];
    53     BFS();
    54     return 0;
    55 }
  • 相关阅读:
    渲染管线
    C++windows内核编程笔记day13 进程、线程与信号量
    稻盛和夫:真正的聪明人,善于把事物简单化
    学会把复杂问题简单化
    任何事物,只要抓住了规律,就等于牵住了牛鼻子
    菩萨奶奶引领我学佛
    数据库每分钟运行监控SQL
    MySQL 从库down机
    sql server 跟踪日志
    胡小林:把日常生活中碰到的事变成我们发露忏悔的机会
  • 原文地址:https://www.cnblogs.com/OIerPrime/p/8407350.html
Copyright © 2020-2023  润新知