12113:Overlapping Squares

Overlapping Squares

我的思路:可以根据所给图形计算出图形中包含的方块的个数以及它们各自的位置,方块可以根据某一个角点的位置来确定,具体方法见 count() 函数。方块确定之后,图形的各种变化就取决于方块们的不同放置顺序了,枚举所有排列,进行模拟,看看模拟结果里面有没有所给图形即可。

思路没什么问题,代码了检查了好多遍,但是一直WA,暂时还没发现问题,再想想吧。

#include<bits/stdc++.h>
using namespace std;
const int maxn = 10;
const int m = 5, n = 9;
typedef pair<int,int> P;
P ps[maxn];
int ok = 0;
int ns, vis[maxn], found[m][n];
char G[m][n+5], R[m][n+1];

int count(){
    int cnt = 0;
    for(int i = 0; i < m; i++){
        for(int j = 0; j < n; j++){
            if(i < m-2 && j < n-4 && G[i][j+1] == '_' && G[i+1][j] == '|'){
                found[i][j] =  1;
                ps[cnt++] = P(i, j);
            }
            else if(i < m-2 && j >= 4 && G[i][j-1] == '_' && G[i+1][j] == '|'){
                if(found[i][j-4]) continue;
                found[i][j-4] = 1;
                ps[cnt++] = P(i, j - 4);
            }
            else if(i >= 2 && j < n-4 && G[i][j+1] == '_' && G[i-1][j] == '|'){
                if(found[i-2][j]) continue;
                found[i-2][j] = 1;
                ps[cnt++] = P(i - 2, j);
            }
            else if(i >= 2 && j >= 4 && G[i][j-1] == '_' && G[i-1][j] == '|'){
                if(found[i-2][j-4]) continue;
                found[i-2][j-4] = 1;
                ps[cnt++] = P(i - 2, j - 4);
            }
        }
    }
    return cnt;
}

int DFS(int i, int num){
    int x = ps[i].first, y = ps[i].second;
    for(int i = 1; i <= 2; i++){
        R[x+i][y] = R[x+i][y+4] = '|';
    }
    for(int i = 1; i <= 3; i += 2){
        R[x][y+i] = R[x+2][y+i] = '_';
    }
    for(int j = 1; j <= 3; j++){
        R[x+1][y+j] = ' ';
        if(R[x+2][y+j] == '|') R[x+2][y+j] = ' ';
    }
    if(num == ns){
        int ok = 1;
        for(int i = 0; i < m && ok; i++){
            for(int j = 0; j < n && ok; j++){
                if(G[i][j] != R[i][j]) ok = 0;
            }
        }
        return ok;
    }

    for(int i = 0; i < ns; i++){
        if(!vis[i]){
            vis[i] = 1;
            if(DFS(i, num + 1)) return 1;
            vis[i] = 0;
        }
    }
    return 0;
}

int main()
{
    freopen("data.in","r",stdin);
    freopen("data.out","w",stdout);
    int T = 0;
    while(fgets(G[0], 15, stdin) && G[0][0] != '0'){
        for(int i = 1; i < m; i++){
            fgets(G[i], 15, stdin);
        }
        memset(found, 0, sizeof(found));
        ns = count();
        // printf("\nns: %d\n", ns);
        ok = 0;
        for(int i = 0; i < m; i++){
            for(int j = 0; j < n; j++){
                R[i][j] = ' ';
            }
            R[i][n] = 0;
        }
        if(ns >= 1 && ns <= 6){
            for(int i = 0; i < ns; i++){
                vis[i] = 1;
                if(DFS(i, 1)){ ok = 1; break; }
                vis[i] = 0;
            }
        }
        printf("Case %d: %s\n", ++T, ok ? "Yes" : "No");
    }
    return 0;
}

 

转载于:https://www.cnblogs.com/JingwangLi/p/10203182.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值