1 条题解

  • 0
    @ 2026-5-8 15:19:12

    完整题解(C++ 版本)

    问题重述

    我们需要用 ww 个白瓶和 bb 个黑瓶搭建一个边长为 kk 的三角形框架。

    • 边长为 kk 的三角形需要 S=k(k+1)2S = \frac{k(k+1)}{2} 个球瓶
    • 同一行的球瓶颜色必须相同
    • 不同行的颜色可以不同
    • 目标是最大化 kk

    关键观察

    重要结论:对于集合 {1,2,,k}\{1, 2, \dots, k\},它的所有子集和可以覆盖从 00SS 的所有整数。

    这意味着:对于任意一个 AA 满足 0AS0 \le A \le S,我们都能找到 {1,2,,k}\{1, 2, \dots, k\} 的一个子集,其元素和正好等于 AA

    可行性分析

    设白瓶使用的行号集合和为 AA,则黑瓶使用的行号集合和为 SAS - A

    我们需要:

    • AwA \le w(白瓶够用)
    • SAbS - A \le b(黑瓶够用)

    即: [ S - b \le A \le w ]

    同时 AA 必须是 00SS 之间的某个整数,且由于子集和的可覆盖性,只要这个区间非空,就存在可行的 AA

    区间 [Sb,w][S-b, w] 非空的条件是: [ S - b \le w \quad \text{且} \quad S - b \le S \quad \text{(自动满足)} ]

    SbwS - b \le w 等价于: [ S \le w + b ]

    结论:可行条件就是总球瓶数足够: [ \boxed{\frac{k(k+1)}{2} \le w + b} ]

    求解最大 kk

    解二次不等式: [ k^2 + k - 2(w+b) \le 0 ]

    得到: [ k \le \frac{-1 + \sqrt{1 + 8(w+b)}}{2} ]

    因此: [ k_{\max} = \left\lfloor \frac{-1 + \sqrt{1 + 8(w+b)}}{2} \right\rfloor ]

    时间复杂度

    每个测试用例 O(1)O(1) 时间,总复杂度 O(t)O(t)

    注意事项

    • w,b109w, b \le 10^9,所以 w+bw+b 最大可达 2×1092 \times 10^9,需要用 long long 类型
    • 使用 sqrt 函数计算平方根,结果取整即可

    完整代码(带注释)

    #include <iostream>
    #include <cmath>
    using namespace std;
    
    int main() {
        int t;
        cin >> t;
        
        while (t--) {
            long long w, b;
            cin >> w >> b;
            
            long long total = w + b;  // 总球瓶数
            
            // 解方程 k(k+1)/2 <= total
            // 即 k^2 + k - 2*total <= 0
            // k = floor((-1 + sqrt(1 + 8*total)) / 2)
            long long k = (sqrt(1 + 8 * total) - 1) / 2;
            
            cout << k << endl;
        }
        
        return 0;
    }
    
    • 1

    信息

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