• ACWING 95 费解的开关 解题记录


    你玩过“拉灯”游戏吗?25盏灯排成一个5x5的方形。每一个灯都有一个开关,游戏者可以改变它的状态。每一步,游戏者可以改变某一个灯的状态。游戏者改变一个灯的状态会产生连锁反应:和这个灯上下左右相邻的灯也要相应地改变其状态。
    
    我们用数字“1”表示一盏开着的灯,用数字“0”表示关着的灯。下面这种状态
    
    10111
    01101
    10111
    10000
    11011
    在改变了最左上角的灯的状态后将变成:
    
    01111
    11101
    10111
    10000
    11011
    再改变它正中间的灯后状态将变成:
    
    01111
    11001
    11001
    10100
    11011
    给定一些游戏的初始状态,编写程序判断游戏者是否可能在6步以内使所有的灯都变亮。
    
    输入格式
    第一行输入正整数n,代表数据中共有n个待解决的游戏初始状态。
    
    以下若干行数据分为n组,每组数据有5行,每行5个字符。每组数据描述了一个游戏的初始状态。各组数据间用一个空行分隔。
    
    输出格式
    一共输出n行数据,每行有一个小于等于6的整数,它表示对于输入数据中对应的游戏状态最少需要几步才能使所有灯变亮。
    
    对于某一个游戏初始状态,若6步以内无法使所有灯变亮,则输出“-1”。
    
    数据范围
    0<n≤500
    输入样例:
    3
    00111
    01011
    10001
    11010
    11100
    
    11101
    11101
    11110
    11111
    11111
    
    01111
    11111
    11111
    11111
    11111
    输出样例:
    
    3
    2
    -1

    https://www.acwing.com/problem/content/97/

     1 #include <iostream>
     2 #include <cstring>
     3 
     4 using namespace std;
     5 
     6 const int INF = 100000;
     7 
     8 char g[10][10];
     9 int dx[5] = {0, -1, 0, 1, 0}, dy[5] = {0, 0, 1, 0, -1};
    10 
    11 void turn(int x, int y)
    12 {
    13     for (int i = 0; i < 5; i ++ )
    14     {
    15         int a = x + dx[i], b = y + dy[i];
    16         if (a >= 0 && a < 5 && b >= 0 && b < 5)
    17         {
    18             g[a][b] = '0' + !(g[a][b] - '0');
    19         }
    20     }
    21 }
    22 
    23 int work()
    24 {
    25     int ans = INF;
    26     for (int k = 0; k < 1 << 5; k ++ )
    27     {
    28         int res = 0;
    29         char backup[10][10];
    30         memcpy(backup, g, sizeof g);
    31 
    32         for (int j = 0; j < 5; j ++ )
    33         {
    34             if (k >> j & 1)
    35             {
    36                 res ++ ;
    37                 turn(0, j);
    38             }
    39         }
    40 
    41         for (int i = 0; i < 4; i ++ )
    42             for (int j = 0; j < 5; j ++ )
    43                 if (g[i][j] == '0')
    44                 {
    45                     res ++ ;
    46                     turn(i + 1, j);
    47                 }
    48 
    49         bool is_successful = true;
    50         for (int j = 0; j < 5; j ++ )
    51             if (g[4][j] == '0')
    52             {
    53                 is_successful = false;
    54                 break;
    55             }
    56 
    57         if (is_successful) ans = min(ans, res);
    58 
    59         memcpy(g, backup, sizeof g);
    60     }
    61 
    62     if (ans > 6) return -1;
    63     return ans;
    64 }
    65 
    66 int main()
    67 {
    68     int T;
    69     cin >> T;
    70     while (T -- )
    71     {
    72         for (int i = 0; i < 5; i ++ ) cin >> g[i];
    73         cout << work() << endl;
    74     }
    75     return 0;
    76 }
    View Code
    作 者: itdef
    欢迎转帖 请保持文本完整并注明出处
    技术博客 http://www.cnblogs.com/itdef/
    B站算法视频题解
    https://space.bilibili.com/18508846
    qq 151435887
    gitee https://gitee.com/def/
    欢迎c c++ 算法爱好者 windows驱动爱好者 服务器程序员沟通交流
    如果觉得不错,欢迎点赞,你的鼓励就是我的动力
    阿里打赏 微信打赏
  • 相关阅读:
    Thinkphp各种方法知识图谱
    Yii2.0学习笔记:创建登录表单
    Yii2.0学习笔记:第一个页面Saying Hello
    4.1
    4
    flask(3.0)
    flask(2.0)
    flask(1.1)装饰器装饰多个视图函数出现的问题
    flask(1.0)
    Flask之上下文管理机制
  • 原文地址:https://www.cnblogs.com/itdef/p/10803891.html
Copyright © 2020-2023  润新知