当前位置: 首页 > news >正文

B3791 [信息与未来 2023] 电路布线

一、题目情况

这道题目的题目情况是这样的:

众所周知,动态规划+搜索这玩意不是给人做的,所以——

我的代码(草履虫版),应运而生——

并且,成功拿到了——

85分(考场17pts)。

二、得分情况

三、评分标准

在你的布线方案合法(连通且无回路)的前提下:

  • 如果你的方案是最优布线方案,即布线的格子最多,该测试点得满分。
  • 否则,该测试点得一半分数。

本题原始满分为 20pts。

四、得分情况

我的得分情况:7AC+3WA(50%分数)

7*10+3*5=70+15=85(pts)=17(考场pts) 

五、具体思路

现在是具体思路。

省赛最后一题最常出:模拟、大数据、人工智能、贪心、最优解等题目。

首先需要知道的是,2023年这一题无论是拿满分的搜索动归还是拿大分的模拟,都有相当可观的代码量,且思路复杂,细节较多,需要预留较多的时间。

对于 100% 的数据,满足 1≤n,m≤6。

所以,大规模的递归和n^3 的循环完全可以接受。

以下展示了一种合法和两种不合法的布线方案:

#+.+.# #.+..# #++..#
+++++# ..+++# .++++#
.+#### .+#### .+####
.++++# .+...# .+...#
合法 不连通 有回路

代码最大的难点就在于对合法与最优解的判断。

怎么办呢?

以下是具体步骤—— 

1.将所有点全部变成"+"

             "#">>-1; 不能改动
             "+">>0 ; 不能改动
             ".">>1 ; 可以改动,需要判断回路问题


2.判断可以删除的"+",(有回路问题)


3.判断可以增加的"+"。


规则:


1.原数组,不进行改变
2.设置2个数组
3.数字全部设置成字符,不要变成数字,会增加代码复杂度

对于回路问题的判断:


1.建立t数组,初始赋值0
2.递归四方向遍历查找
规则:
1.如果碰到-1,返回false
2.只要某函数出现返回false的情况,之后的所有函数都是false。
3.记录上一次函数所使用的方向
4.如果在与上一次函数所使用方向不矛盾的情况下仍遇到了-1则返回false。
x   y
1 |  0 右
-1|  0 左
0 |  1 下
0 | -1 上
85pts(考场=85*0.2=17分) 蓝题

#include <bits/stdc++.h>
using namespace std;
//常用变量
int n,m;
char y[10][10]; 
char b[10][10];
int dx[5]={1,-1,0,0};
int dy[5]={0,0,1,-1};
//局部变量 
int S;
int t[10][10];
bool Err(int x,int y,int last,int sh)//判断回路问题
{//模板t[x][y]=0;sh--;if(sh==0) return 0;for(int i=0; i<4; i++){if((i==0&&last==1)||(i==1&&last==0)||(i==2&&last==3)||(i==3&&last==2)) continue;int lx=x+dx[i];int ly=y+dy[i];if(lx<1||lx>n||ly<1||ly>m) continue;else if(b[lx][ly]=='+'){if(t[lx][ly]==0) return 1;else if(Err(lx,ly,i,sh)==1) return 1;}}return 0;
}
void out()//输出
{for(int i=1; i<=n; i++){for(int j=1; j<=m; j++) cout<<b[i][j];cout<<'\n';}
}
void go()//刚开始的删除,不合法就删
{for(int i=1; i<=n; i++){for(int j=1; j<=m; j++){memset(t,-1,sizeof(t));int ans=Err(i,j,-1,S);if(y[i][j]=='.'&&ans==1){b[i][j]='.';S--;}/*out();for(int i=1; i<=n; i++){for(int j=1; j<=m; j++) cout<<setw(2)<<t[i][j];cout<<'\n';}cout<<'\n';system("pause");*/}}
}
void more()//再遍历一次,增加还能加上的地方
{for(int i=1; i<=n; i++){for(int j=1; j<=m; j++){if(y[i][j]=='.'&&b[i][j]=='.'){b[i][j]='+';S++;memset(t,-1,sizeof(t));int ans=Err(i,j,-1,S);if(ans==1){b[i][j]='.';S--;}}}}
}
int main()
{ios::sync_with_stdio(0);cin.tie(0),cout.tie(0);cin>>n>>m;for(int i=1; i<=n; i++){for(int j=1; j<=m; j++){cin>>y[i][j];b[i][j]=y[i][j];if(b[i][j]=='.') b[i][j]='+';if(b[i][j]=='+') S++;}}go();more();out();return 0;
}

#include <bits/stdc++.h>
using namespace std;
//常用变量
int n,m;
char y[10][10]; 
char b[10][10];
int dx[5]={1,-1,0,0};
int dy[5]={0,0,1,-1};
//局部变量 
int S;
int t[10][10];
bool Err(int x,int y,int last,int sh)
{
    t[x][y]=0;
    sh--;
    if(sh==0) return 0;
    for(int i=0; i<4; i++)
    {
        if((i==0&&last==1)||(i==1&&last==0)||(i==2&&last==3)||(i==3&&last==2)) continue;
        int lx=x+dx[i];
        int ly=y+dy[i];
        if(lx<1||lx>n||ly<1||ly>m) continue;
        else if(b[lx][ly]=='+')
        {
            if(t[lx][ly]==0) return 1;
            else if(Err(lx,ly,i,sh)==1) return 1;
        }
    }
    return 0;
}
void out()
{
    for(int i=1; i<=n; i++)
    {
        for(int j=1; j<=m; j++) cout<<b[i][j];
        cout<<'\n';
    }
}
void go()
{
    for(int i=1; i<=n; i++)
    {
        for(int j=1; j<=m; j++)
        {
            memset(t,-1,sizeof(t));
            int ans=Err(i,j,-1,S);
            if(y[i][j]=='.'&&ans==1)
            {
                b[i][j]='.';
                S--;
            }
            /*
            out();
            for(int i=1; i<=n; i++)
            {
                for(int j=1; j<=m; j++) cout<<setw(2)<<t[i][j];
                cout<<'\n';
            }
            cout<<'\n';
            system("pause");
            */
        }
    }
}
void more()
{
    for(int i=1; i<=n; i++)
    {
        for(int j=1; j<=m; j++)
        {
            if(y[i][j]=='.'&&b[i][j]=='.')
            {
                b[i][j]='+';
                S++;
                memset(t,-1,sizeof(t));
                int ans=Err(i,j,-1,S);
                if(ans==1)
                {
                    b[i][j]='.';
                    S--;
                }
            }
        }
    }
}
int main()
{
    ios::sync_with_stdio(0);
    cin.tie(0),cout.tie(0);
    cin>>n>>m;
    for(int i=1; i<=n; i++)
    {
        for(int j=1; j<=m; j++)
        {
            cin>>y[i][j];
            b[i][j]=y[i][j];
            if(b[i][j]=='.') b[i][j]='+';
            if(b[i][j]=='+') S++;
        }
    }
    go();
    more();
    out();
    return 0;

2023年的虽然已经过去,但到现在仍然很有参考价值,这道题能到达 考场分10pts 以上的可以挑战2024年总分80pts。2025,祝大家信息与未来扶摇直上,逢考必过,蛇年好运!

http://www.xdnf.cn/news/164755.html

相关文章:

  • c++-模板
  • 2.4.5goweb项目上传到csdn的git仓库
  • 【量化交易笔记】17.多因子的线性回归模型策略
  • 提取office最强悍的软件
  • asammdf 库的文件操作和数据导出:高效管理 MDF 文件
  • 刚体运动 (位置向量 - 旋转矩阵) 笔记 1.1~1.3 (台大机器人学-林沛群)
  • 职场十二法则-马方
  • AnimateCC教学:元件旋转当中平移
  • 桥接模式(Bridge Pattern)详解
  • 从OpenAI收购实时数据引擎揭示AI数据库进化方向
  • ARM架构的微控制器总线矩阵仲裁策略
  • Java基础语法10分钟速成
  • JAVA:线程安全问题及解决方案
  • Centos7系统防火墙使用教程
  • 【JavaScript】自增和自减、逻辑运算符
  • 五年经验Java开发如何破局创业
  • L1-5 这是字符串题
  • # **DeepSeek 保姆级使用教程**
  • Redis数据结构SDS,IntSet,Dict
  • Java—— 五道算法水题
  • 强化学习基础
  • Python AI图像生成方案指南
  • Axure疑难杂症:全局变量典型应用及思考逻辑(玩转全局变量)
  • 剑指offer经典题目(六)
  • 做的一些题目的答案和自己的一些思考
  • LangChain 中的 Task(任务) 主要通过 生成器(Generator) 实现,而非传统的迭代器(Iterator)
  • Ardunio学习
  • 推论阶梯——AI与思维模型【81】
  • Redis 数据分片三大方案深度解析与 Java 实战
  • JavaScript原生实现简单虚拟列表(列表不定高)