AcWing《蓝桥杯集训·每日一题》—— 3777 砖块

文章介绍了AcWing《蓝桥杯集训·每日一题》中的3777号问题——砖块。题目要求通过不超过3n次操作,使所有砖块颜色一致。解题思路涉及对砖块颜色的统计和奇偶性分析,以及提供了一段Python代码实现。文章提供了输入输出样例,并讨论了代码的时间复杂度。
摘要由CSDN通过智能技术生成

AcWing《蓝桥杯集训·每日一题》—— 3777. 砖块

本次博客我是通过Notion软件写的,转md文件可能不太美观,大家可以去我的博客中查看:北天的 BLOG,持续更新中,另外这是我创建的编程学习小组频道,想一起学习的朋友可以一起!!!

一、题目

每个砖块要么是黑色的,要么是白色的。

现在你可以进行以下操作若干次(可以是 0 次):

选择两个相邻的砖块,反转它们的颜色。(黑变白,白变黑)

你的目标是通过不超过  3 n 3n 3n 次操作,将所有砖块的颜色变得一致。

输入格式

第一行包含整数  T T T,表示共有  T T T 组测试数据。

每组数据第一行包含一个整数  n n n

第二行包含一个长度为  n n n 的字符串  s s s。其中的每个字符都是 W 或 B,如果第  i i i 个字符是 W,则表示第  i i i 号砖块是白色的,如果第  i i i 个字符是 B,则表示第  i i i 个砖块是黑色的。

输出格式

每组数据,如果无解则输出一行 −1

否则,首先输出一行  k k k,表示需要的操作次数。

如果  k > 0 k>0 k>0,则还需再输出一行  k k k 个整数, p 1 , p 2 , … , p k p1,p2,…,pk p1,p2,,pk。其中  p i p_i pi 表示第  i i i 次操作,选中的砖块为  p i p_i pi 和  p i + 1 p_i+1 pi+1 号砖块。

如果方案不唯一,则输出任意合理方案即可。

数据范围

1 ≤ T ≤ 10 1≤T≤10 1T10

2 ≤ n ≤ 200 2≤n≤200 2n200

输入样例:

4
8
BWWWWWWB
4
BWBB
5
WWWWW
3
BWB

输出样例:

3
6 2 4
-1
0
2
2 1

二、解题思路

这道题目需要我们实现的是对给定字符串s进行操作,使得其变成一个全为’B’或全为’W’的字符串,并输出操作次数以及具体的操作。操作规则为,如果s中’B’和’W’个数均为偶数,则不需要进行任何操作;如果’B’个数为奇数,需要对相邻的两个’B’进行操作,使其变成’W’,或者将’B’和’W’对调,使得’B’个数变为偶数,然后进行相邻的’B’操作,使其变成’W’。如果’W’个数为奇数,操作方法与’B’个数奇数的情况相似。

具体来说,我们在实现的过程是先计算’B’和’W’的个数,然后根据个数的奇偶性进行分类讨论。当’B’和’W’的个数均为偶数时,不需要操作。当其中一个为奇数时,需要对相邻的两个颜色相同的块进行操作,使其变成相反的颜色,或者将两个不同颜色的块进行对调,使得颜色个数为偶数。通过循环操作后,最终得到一个全为’B’或者全为’W’的字符串。最后输出操作次数和具体操作的序列。

三、解题思路

# 输入测试用例数量
T = int(input())
for _ in range(T):
    # 输入字符串长度和字符串
    n = int(input())
    s = list(input())

    # 统计W和B的数量
    w_cnt = s.count('W')
    b_cnt = s.count('B')

    # 判断是否有解
    if w_cnt % 2 == 1 and b_cnt % 2 == 1:
        print(-1) # 没有解
    else:
        res_cnt = 0 # 记录需要操作的次数
        res = [] # 记录操作的位置

        if w_cnt % 2 == 1: # W的数量为奇数,需要将一些B变成W
            i = 0
            while i < n - 1:
                if s[i] == 'B' and s[i+1] == 'B': # 连续的两个B都变成W
                    s[i] = 'W'
                    s[i+1] = 'W'
                    res_cnt += 1
                    res.append(i + 1)
                    i += 2
                elif s[i] == 'B' and s[i+1] == 'W': # 只将前面的B变成W
                    s[i] = 'W'
                    s[i+1] = 'B'
                    res_cnt += 1
                    res.append(i + 1)
                    i += 1
                elif s[i] == 'W': # 如果是W则不用操作
                    i += 1
        else: # B的数量为奇数,需要将一些W变成B
            i = 0
            while i < n - 1:
                if s[i] == 'W' and s[i+1] == 'W': # 连续的两个W都变成B
                    s[i] = 'B'
                    s[i+1] = 'B'
                    res_cnt += 1
                    res.append(i + 1)
                    i += 2
                elif s[i] == 'W' and s[i+1] == 'B': # 只将前面的W变成B
                    s[i] = 'B'
                    s[i+1] = 'W'
                    res_cnt += 1
                    res.append(i + 1)
                    i += 1
                elif s[i] == 'B': # 如果是B则不用操作
                    i += 1

        # 输出结果
        if res_cnt > 0:
            print(res_cnt)
            for x in res:
                print(x, end = ' ')
            print()
        else:
            print(0)

这段代码的时间复杂度为 O ( T n ) O(Tn) O(Tn),其中 T T T是测试用例的数量, n n n是输入字符串的长度。这是因为代码中有一个外层循环,循环 T T T次,而每次循环中都要对长度为 n n n的输入字符串进行遍历,所以总时间复杂度是 O ( T n ) O(Tn) O(Tn)

在代码中,使用了一些内置函数和操作,如**s.count()s[i]**等,这些操作的时间复杂度较低,可以忽略不计。因此,这段代码的主要瓶颈在于对输入字符串的遍历和修改操作。

如果要优化这段代码的时间复杂度,可能需要重新设计算法。可以考虑一些贪心策略,如将相邻的不同颜色的棋子互换,使得相邻的棋子颜色相同。这样可以尽可能地减少需要修改的棋子数量。但这个算法的正确性需要进行证明,同时实现也可能会比较复杂。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

-北天-

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值