回文子序列 ssl2662 暴力

53 篇文章 0 订阅

Description


回文序列是指左右对称的序列。例如1 2 3 2 1是回文序列,但是1 2 3 2 2就不是。我们会给定一个N×M的矩阵,你需要从这个矩阵中找出一个P×P的子矩阵,使得这个子矩阵的每一列和每一行都是回文序列。

Solution


果然竞赛要有信仰→

任意一个回文的矩形都是可以由小一圈的回文矩形+最外圈上都是回文串,那么这样子 O(n3) 暴力一下判断就行了。如果还想快一点可以预处理回文的情况,但这样就要考虑MLE了

Code


#include <stdio.h>
#define rep(i, st, ed) for (int i = st; i <= ed; i += 1)
#define min(x, y) (x)<(y)?(x):(y)
#define N 301
int rc[N][N];
bool isPr[N][N][N];
int main(void){
    int n, m;
    scanf("%d%d", &n, &m);
    rep(i, 1, n){
        rep(j, 1, m){
            scanf("%d", &rc[i][j]);
            isPr[i][j][1] = 1;
        }
    }
    rep(i, 1, n - 1){
        rep(j, 1, m - 1){
            if (rc[i][j] == rc[i + 1][j] && rc[i][j] == rc[i][j + 1] && rc[i][j] == rc[i + 1][j + 1]){
                isPr[i][j][2] = 1;
            }
        }
    }
    int ans = 0;
    int mn = min(n, m);
    rep(k, 1, mn){
        rep(i, 2, n - k){
            rep(j, 2, m - k){
                if (isPr[i][j][k]){
                    bool flag = false;
                    for (int l = j - 1, r = j + k; l <= r; l += 1, r -= 1){
                        if (rc[i - 1][l] ^ rc[i - 1][r] || rc[i + k][l] ^ rc[i + k][r] || rc[i - 1][l] ^ rc[i + k][l] || rc[i - 1][r] ^ rc[i + k][r]){
                            flag = true;
                            break;
                        }
                    }
                    if (flag){
                        continue;
                    }
                    for (int l = i - 1, r = i + k; l <= r; l += 1, r -= 1){
                        if (rc[l][j - 1] ^ rc[r][j - 1] || rc[l][j + k] ^ rc[r][j + k] || rc[l][j - 1] ^ rc[l][j + k] || rc[r][j - 1] ^ rc[r][j + k]){
                            flag = true;
                            break;
                        }
                    }
                    if (!flag){
                        isPr[i - 1][j - 1][k + 2] = 1;
                        if (k + 2 > ans){
                            ans = k + 2;
                        }
                    }
                }
            }
        }
    }
    printf("%d\n", ans);
    return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值