1 条题解

  • 0
    @ 2026-4-6 20:49:30

    问题分析

    我们有一排 nn 个格子,每个格子要么是空(.),要么是阻塞(#)。
    目标:让所有空格子最终都有水。
    允许两种操作:

    1. 在一个空单元格中放置水(操作 11);
    2. 从一个已有水的单元格取出水,并放入任意另一个空单元格(操作 22)。

    此外,有一个自动填充规则:若某个空单元格 ii2in12\le i\le n-1)的左右邻居 i1i-1i+1i+1已经有水,则 ii自动被水填满。

    最少需要执行多少次操作 11。操作 22 次数不限。


    关键观察

    • 如果存在连续三个空单元格 i1,i,i+1i-1, i, i+1,那么我们可以先在 i1i-1i+1i+1 中放置水(两次操作 11),此时 ii 自动填满。
    • 然后,我们可以从 ii 中取出水,放入任意其他空单元格(操作 22)。由于 i1i-1i+1i+1 仍然有水,ii再次自动填满
    • 这意味着:只要有三连空,我们就能用 22 次操作 11 来“复制”出无限多的水,从而填满所有空单元格。
    • 反之,如果没有三连空,那么自动填充规则永远不会被触发(因为任何自动填充都要求三个连续格子均为空,且两侧已经人为放水)。此时必须逐个在所有空单元格中执行操作 11,即操作 11 次数等于空单元格总数。

    算法步骤

    1. 读入测试用例数 tt
    2. 对每个测试用例:
      • 读入 nn 和字符串 ss
      • 初始化 empty_cnt = 0has_three = false
      • 遍历 ii00n1n-1
        • s[i]==.s[i] == '.',则 empty_cnt++
        • 同时检查 i2i \ge 2s[i2]==.s[i-2] == '.'s[i1]==.s[i-1] == '.',若是则 has_three = true
      • has_three == true,输出 22;否则输出 empty_cnt

    时间复杂度 O(n)O(n),空间复杂度 O(1)O(1)(不计输入存储)。


    正确性证明

    情况一:存在三个连续空单元格
    设三个连续空位置为 p,p+1,p+2p, p+1, p+2

    1. ppp+2p+2 中执行操作 11(两次)。此时 p+1p+1 因左右邻居有水而自动填满。
    2. 现在 p,p+1,p+2p, p+1, p+2 都有水。
    3. 对于任意其他空单元格 xx
      • 使用操作 22p+1p+1 取出水,放入 xx
      • 由于 ppp+2p+2 仍然有水,p+1p+1再次自动填满(因为它的左右邻居仍然有水)。
      • 重复此过程,即可用无限次操作 22 将水扩散到所有空单元格。
        因此只需要 22 次操作 11。并且显然不可能少于 22 次(因为至少需要两个水源才能触发自动填充)。

    情况二:不存在三个连续空单元格
    自动填充规则永远不会生效(因为需要三个连续空位,且中间的空位必须左右都有水;但既然没有三个连续空位,任何水都无法通过自动规则传播到新的空单元格)。
    因此,每个空单元格都必须通过操作 11 单独放置水。所以答案就是空单元格的数量。

    边界情况

    • n<3n < 3:不可能有三个连续空位,因此答案直接是空单元格数。
    • 没有空单元格:empty_cnt = 0,输出 00

    示例验证

    以题目给出的测试用例为例:

    1. 3 ...
      存在三个连续空 → 输出 22
    2. 7 ##....#
      子串 "..." 从下标 2244 存在 → 输出 22
    3. 7 ..#.#..
      空位有 55 个,但没有三个连续空 → 输出 55
    4. 4 ####
      空位 00 → 输出 00
    5. 10 #...#..#.#
      空位分布:下标 1,2,3,5,6,81,2,3,5,6,8(共 66 个),但存在 "..." 吗?检查:
      • 下标 1,2,31,2,3... → 存在三连空 → 输出 22

    全部匹配输出。


    复杂度分析

    • 时间:每个测试用例扫描一次字符串,O(n)100×100=104O(\sum n) \le 100 \times 100 = 10^4,轻松通过。
    • 空间:仅使用常数个变量,O(1)O(1)

    总结

    • 核心结论:如果存在三个连续的空单元格,答案为 22;否则答案为空单元格总数
    • 原因:三连空可以借助自动填充和水的移动(操作 22)实现无限复制水,从而仅需最初的两个水源。
    • 实现简单,只需扫描判断是否有 "..." 子串,并统计 '.' 个数即可。
    • 1

    信息

    ID
    6451
    时间
    1000ms
    内存
    256MiB
    难度
    10
    标签
    递交数
    1
    已通过
    1
    上传者