ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

Square Destroyer-POJ 1084 (IDA*)

2019-03-31 21:37:35  阅读:353  来源: 互联网

标签:1084 int matchsticks Square grid input POJ squares size


Description

The left figure below shows a complete 3*3 grid made with 2*(3*4) (=24) matchsticks. The lengths of all matchsticks are one. You can find many squares of different sizes in the grid. The size of a square is the length of its side. In the grid shown in the left figure, there are 9 squares of size one, 4 squares of size two, and 1 square of size three.

Each matchstick of the complete grid is identified with a unique number which is assigned from left to right and from top to bottom as shown in the left figure. If you take some matchsticks out from the complete grid, then some squares in the grid will be destroyed, which results in an incomplete 3*3 grid. The right figure illustrates an incomplete 3*3 grid after removing three matchsticks numbered with 12, 17 and 23. This removal destroys 5 squares of size one, 3 squares of size two, and 1 square of size three. Consequently, the incomplete grid does not have squares of size three, but still has 4 squares of size one and 1 square of size two.

As input, you are given a (complete or incomplete) n*n grid made with no more than 2n(n+1) matchsticks for a natural number 5 <= n . Your task is to compute the minimum number of matchsticks taken
out to destroy all the squares existing in the input n*n grid.

Input

The input consists of T test cases. The number of test cases (T ) is given in the first line of the input file.
Each test case consists of two lines: The first line contains a natural number n , not greater than 5, which implies you are given a (complete or incomplete) n*n grid as input, and the second line begins with a nonnegative integer k , the number of matchsticks that are missing from the complete n*n grid, followed by
k numbers specifying the matchsticks. Note that if k is equal to zero, then the input grid is a complete n*n grid; otherwise, the input grid is an incomplete n*n grid such that the specified k matchsticks are missing from the complete n*n grid.

Output

Print exactly one line for each test case. The line should contain the minimum number of matchsticks that have to be taken out to destroy all the squares in the input grid.

Sample Input

2
2
0
3
3 12 17 23

Sample Output

3
3

题意:t组数据,给出n代表n*n的网格,给一个值k,然后k个值,表示去掉k所代表的边,问还需要最少去掉几条边可以使得网格中没有正方形。

思路: 

评估函数:每出现一个正方形,就删去其含有的边,然后继续扫描正方形,这样计数出来的次数比实际需要次数小(因为一次删去了多条边)

对于网格中正方形的枚举:

①先枚举正方形大小,1 <= size <= n;

②枚举网格每行最左边的火柴

③对于每个行位置,枚举该行可以成为该size大小正方形的最左边火柴

④标记该正方形的所有上边界和下边界(知道size和上边界最左火柴很容易求得)

 标记该正方形的所有左边界和有边界

 

(代码借鉴网上,侵删)

#include<iostream>
#include<cstdio>
#include<vector>
#include<cstring>
using namespace std;

int t;
int totsquare,totstick,base;
vector<int>stick[65],square[65];
int n,k;
int ans;
int exi[65],tmp[65];

int cal()
{
    int res = 0;
    for(int i=1;i<=totsquare;i++)tmp[i] = exi[i];
    for(int i=1;i<=totsquare;i++)if(!tmp[i])
    {
        res++;
        for(int j=0;j<square[i].size();j++)
        {
            for(int l=0;l<stick[square[i][j]].size();l++)
            {
                tmp[stick[square[i][j]][l]]--;
            }
        }
    }
    return res;
}

bool dfs(int sum,int lim)
{
    if(sum + cal() > lim)return 0;
    int tmp = 1;
    while(exi[tmp] < 0 && tmp <= totsquare)tmp++;
    if(tmp > totsquare)
    {
        ans = min(ans,sum);
        return 1;
    }
    for(int i=0;i<square[tmp].size();i++)
    {
        int sti = square[tmp][i];
        for(int j=0;j<stick[sti].size();j++)
        {
            exi[stick[sti][j]]--;
        }
        if(dfs(sum+1,lim))return 1;
        for(int j=0;j<stick[sti].size();j++)
        {
            exi[stick[sti][j]]++;
        }
    }
    return 0;
}
int main()
{
    scanf("%d",&t);
    while(t--)
    {
        scanf("%d%d",&n,&k);
        totsquare = 0,totstick = 2*n*(n+1),base = 2*n+1;
        for(int i=1; i<65; i++)
        {
            stick[i].clear();
            square[i].clear();
        }
        for(int sz=1; sz<=n; sz++)
        {
            for(int i=1; (i-1)/base+sz<=n; i+=base)
            {
                for(int j=i; j-i+sz<=n; j++)
                {
                    totsquare++;
                    for(int l=j; l-j<sz; l++)
                    {
                        square[totsquare].push_back(l);
                        square[totsquare].push_back(l+sz*base);
                        stick[l].push_back(totsquare);
                        stick[l+sz*base].push_back(totsquare);
                    }
                    for(int l=j+n; (l-j-sz)/base<sz; l+=base)
                    {
                        square[totsquare].push_back(l);
                        square[totsquare].push_back(l+sz);
                        stick[l].push_back(totsquare);
                        stick[l+sz].push_back(totsquare);
                    }
                }
            }
        }
        memset(exi,0,sizeof(exi));
        for(int i=1; i<=k; i++)
        {
            int t_st;
            scanf("%d",&t_st);
            for(int j=0; j<stick[t_st].size(); j++)
            {
                exi[stick[t_st][j]]--;
            }
            totstick--;
        }
        ans = totstick;
        for(int maxd=0;; maxd++)
        {
            if(dfs(0,maxd))
            {
                printf("%d\n",ans);
                break;
            }
        }
    }
}
View Code

 

 

 

 

标签:1084,int,matchsticks,Square,grid,input,POJ,squares,size
来源: https://www.cnblogs.com/iwannabe/p/10633322.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有