Codeforces 679C Bear and Square Grid(滑动窗口)
来源:互联网 发布:淘宝上买阅读器怎样 编辑:程序博客网 时间:2024/06/06 12:50
题意:
给定一个网格图,其中有的有的是可以走的点,有的是障碍,定义连通块和无向图中连通块是一样的。如果把一个k*k大小的区域内的点都变成联通块,那么这个网格图中最大的连通块是多大
解法:
这个如果用暴力枚举的话,是
O(N4) 的,但是我们可以用滑动窗口来优化,我们首先把每一个连通块的大小求出来,然后枚举y,先把窗口内的点全部变为联通,并且从他所在的连通块分离出去,那么我们只需要检测当前连通块的上下左右四条边所连接的连通块来更新答案即可,因为一个连通块可能被统计很多次,所以我们要给每一个连通块打一个时间戳,来标记是否被当前情况添加过。具体可以看代码。
//// Created by CQU_CST_WuErli// Copyright (c) 2016 CQU_CST_WuErli. All rights reserved.////#pragma comment(linker, "/STACK:102400000,102400000")#include <iostream>#include <cstring>#include <cstdio>#include <cstdlib>#include <cctype>#include <cmath>#include <string>#include <vector>#include <map>#include <queue>#include <stack>#include <set>#include <algorithm>#include <sstream>#define CLR(x) memset(x,0,sizeof(x))#define OFF(x) memset(x,-1,sizeof(x))#define MEM(x,a) memset((x),(a),sizeof(x))#define BUG cout << "I am here" << endl#define lookln(x) cout << #x << "=" << x << endl#define SI(a) scanf("%d", &a)#define SII(a,b) scanf("%d%d", &a, &b)#define SIII(a,b,c) scanf("%d%d%d", &a, &b, &c)const int INF_INT=0x3f3f3f3f;const long long INF_LL=0x7f7f7f7f;const int MOD=1e9+7;const double eps=1e-10;const double pi=acos(-1);typedef long long ll;using namespace std;int n, k;char mp[555][555];int vis[555][555];int size[555 * 555];int tid[555 * 555];int cnt;int dir[4][2] = {1, 0, 0, 1, -1, 0, 0, -1};int sum;void dfs(int x, int y) { vis[x][y] = cnt; sum++; for (int i = 0; i < 4; i++) { int tx = x + dir[i][0], ty = y + dir[i][1]; if (tx < 1 || ty < 1 || tx > n || ty > n || mp[tx][ty] == 'X' || vis[tx][ty]) continue; dfs(tx, ty); }}void add(int x, int y, int ti, int& ans) { if (x < 1 || x > n || y < 1 || y > n || mp[x][y] == 'X') return; if (tid[vis[x][y]] != ti) { ans += size[vis[x][y]]; tid[vis[x][y]] = ti; }}int main(int argc, char const *argv[]) {#ifdef LOCAL freopen("C:\\Users\\john\\Desktop\\in.txt","r",stdin); // freopen("C:\\Users\\john\\Desktop\\out.txt","w",stdout);#endif while(SII(n, k) ==2) { for (int i = 1; i <= n; i++) scanf("%s", mp[i] + 1); CLR(vis); CLR(size); CLR(tid); int ti = 1; cnt = 0; for (int i = 1; i <= n; i++) { for (int j = 1; j <= n; j++) if (mp[i][j] == '.' && !vis[i][j]) { cnt++; sum = 0; dfs(i, j); size[cnt] = sum; } } int ans = 0; for (int y = 1; y + k - 1<= n; y++) { for (int x = 1; x <= k; x++) { for (int i = 0; i < k; i++) { size[vis[x][y + i]]--; } } for (int x = 1; x + k - 1<= n; x++) { int tmp = k * k; for (int i = x; i < x + k; i++) { add(i, y - 1, ti, tmp); add(i, y + k, ti, tmp); } for (int i = y; i < y + k; i++) { add(x - 1, i, ti, tmp); add(x + k, i, ti, tmp); } ti++; ans = max(tmp, ans); if (x + k <= n) { for (int i = y; i < y + k; i++) { size[vis[x][i]]++; size[vis[x + k][i]]--; } } } for (int i = n - k + 1; i <= n; i++) { for (int j = y; j < y + k; j++) { size[vis[i][j]]++; } } } cout << ans << endl; } return 0;}
0 0
- Codeforces 679C Bear and Square Grid(滑动窗口)
- Codeforces 679C Bear and Square Grid 暴力(滑动窗口)
- CodeForces 679C - Bear and Square Grid
- Codeforces 679C Bear and Square Grid(枚举 标记)
- Codeforces Round #356 (Div. 2) Bear and Square Grid
- Codeforces Round #356 (Div. 2)E. Bear and Square Grid
- Codeforces Round #356 (Div. 2) Bear and Square Grid ★ ★ ★
- Codeforces Round #356 (Div. 2) E. Bear and Square Grid 滑块
- codeforces_679C. Bear and Square Grid(滑块)
- Codeforces 385 C. Bear and Prime Numbers
- CodeForces 385C Bear and Prime Numbers
- Codeforces 385C Bear and Prime Numbers
- Codeforces 385 C Bear and Prime Numbers
- codeforces 385C Bear and Prime Numbers
- CodeForces 574C - Bear and Poker
- Codeforces Round #318 C - Bear and Poker
- CodeForces #318 (div1) C.Bear and Drawing
- Codeforces Round #318-(C. Bear and Poker)
- LEAPMotion猎户座(VR)开发~003~UI
- HDU 1075 What Are You Talking About (字典树)
- Boost C++ Libraries 遍历文件目录
- 2017年计划
- python多行字符串拼接使用小括号
- Codeforces 679C Bear and Square Grid(滑动窗口)
- library cache lock 相关的bug list
- Linux下配置vsftp的若干问题
- Struts2校验器详解
- Codeforces 685B Kay and Snowflake(树的重心)
- 代理模式
- bzoj 1031: [JSOI2007]字符加密Cipher
- Hadoop----集群运维(持续更新...)
- Flume的简单了解: