1 条题解

  • 0
    @ 2025-8-24 22:51:03

    自动搬运

    查看原文

    来自洛谷,原作者为

    avatar Fire_flame
    乐观乐观再乐观

    搬运于2025-08-24 22:51:03,当前版本为作者最后更新于2023-06-12 22:38:37,作者可能在搬运后再次修改,您可在原文处查看最新版

    自动搬运只会搬运当前题目点赞数最高的题解,您可前往洛谷题解查看更多

    以下是正文


    Solution\mathbf{Solution}

    子任务 11:因为平均数小于等于 33,也就是说不会出现 55,输出 00 即可。


    子任务 22:平均数是 55,最大值也不超过 55,也就是说 a1=a2==an=5a_1=a_2=\dots=a_n=5

    那么答案即为:

    l=1nr=ln(rl+1)\sum\limits_{l=1}^{n}\sum\limits_{r=l}^{n}(r-l+1)

    不难发现,枚举左端点 ll,那么以左端点为 ll 的区间的贡献是 (nl+2)×(nl+1)÷2(n - l + 2)\times(n - l + 1)\div 2

    时间复杂度 O(n)O(n)


    子任务 33:枚举左端点,右端点,然后 O(n)O(n) 求解答案即可。

    时间复杂度 O(n3)O(n^3)


    子任务 44

    因为序列单调不上升,而且最大数为 55

    所以如果出现了 55,肯定是只有前面连续的一段。

    即可转化成子任务 22


    子任务 55

    考虑递推,假设当前右端点枚举到了第 rr 位,已经遍历了连续 cntcnt55

    • 如果 ar5a_r\neq5cntcnt 清零,不添加贡献。

    • 如果 ar=5a_r=5,考虑左端点 ll

      1. 首先 cntcnt 要记得加一。
      2. 如果左端点 lrcntl\le r-cnt,每一个区间贡献添加 cntcnt。总贡献添加 (rcnt+1)×cnt(r - cnt + 1) \times cnt
      3. 如果左端点 rcnt+1lrr-cnt+1\le l\le r,总贡献添加 cnt×(cnt1)÷2cnt\times(cnt-1)\div 2

    最后统计答案即可。

    标程:

    #include<bits/stdc++.h>//by Fire_flame
    #define int long long
    using namespace std;
    const int MAXN = 5e5 + 5, MOD = 1e9 + 7;
    int n, ans, cnt, a[MAXN];
    signed main(){
    	scanf("%lld", &n);
    	ans = 0, cnt = 0;
    	for(int i = 1;i <= n;i ++)scanf("%lld", &a[i]);
    	for(int i = 1;i <= n;i ++){
    		if(a[i] == 5)cnt ++;
    		else cnt = 0;
    		ans += (i - cnt + 1) * cnt % MOD + cnt * (cnt - 1) / 2 % MOD;
    		ans %= MOD;
    	}
    	printf("%lld", ans);
    	return 0;
    }
    
    • 1

    信息

    ID
    8756
    时间
    1000ms
    内存
    128MiB
    难度
    2
    标签
    递交数
    0
    已通过
    0
    上传者