王道机试指南 例题9.4 Square

题目:

题目大意:给出一堆长度各异的木条,这些木条能否头尾相连构成一个正方形?

算法及分析:

深度优先遍历。

代码:

#include <iostream>
#include <string>
#include <cstring> //memset函数的头文件
#include <algorithm>

using namespace std;

//设计成全局变量,减少DFS函数的传参数量
const int MAXN=25;
int side;//正方形边长
int m;//木条数
int sticks[MAXN];//记录木条长度
int visit[MAXN];//记录该木条是否访问过

bool DFS(int sum,int count,int position){//深度优先遍历
    if(count==3)
        return true;
    for(int i=position;i<m;i++){
        if(visit[i]==1 || sum+sticks[i]>side)//如果该条边访问过或累加后长度大于正方形边长,则进入下一轮循环
            continue;

        sum+=sticks[i];
        visit[i]=1;
        if(sum==side){//刚好凑成一条边
            if(DFS(0,count+1,0)==1)
                return true;
        }
        else{//sum<side,还不够凑成一条边
            if(DFS(sum,count,i+1)==1)
                return true;
        }
        //本轮构造失败,则恢复sum并恢复访问标记
        sum-=sticks[i];
        visit[i]=0;
    }
    return false;
}

bool compare(int x,int y){//按从大到小排序
    return x>y;
}

int main(){
    int n;
    cin>>n;
    for(int k=0;k<n;k++){
        cin>>m;
        int total=0;
        for(int j=0;j<m;j++){
            cin>>sticks[j];
            total+=sticks[j];
        }

        if(total%4!=0){//剪枝:如果总长度不能被4整除,则构造失败
            cout<<"no"<<endl;
            continue;
        }

        side=total/4;
        sort(sticks,sticks+m,compare);//将木条按长度从大到小排序
        if(sticks[0]>side){//剪枝:如果最长的木条长度超过正方形边长,则构造失败
            cout<<"no"<<endl;
            continue;
        }

        memset(visit,0,sizeof(visit));//初始化访问标记为0
        if(DFS(0,0,0)==1)
            cout<<"yes"<<endl;
        else
            cout<<"no"<<endl;
    }
    return 0;
}

运行结果:

全部评论
感谢楼主的分享
1 回复 分享
发布于 2023-02-13 09:18 陕西
这是哪里的的题目
点赞 回复 分享
发布于 2023-02-13 09:12 江苏

相关推荐

评论
点赞
8
分享

创作者周榜

更多
牛客网
牛客企业服务