首页 > 其他分享 >ABC269F 题解

ABC269F 题解

时间:2024-08-03 11:19:10浏览次数:11  
标签:ll int 题解 sum cin ans ABC269F s1

注意到第 \(i\) 行和第 \(i+2\) 行被删除的格子的排列顺序相同,格子上的数差了 \(2m\)。

于是处理出第 \(i,i+1\) 行的答案 \(a_i,a_{i+1}\),有值的格子的个数 \(c_i,c_{i+1}\)。

令 \(s(i)=\dfrac{(i-1)i}2\),也就是 \(\sum_{j=1}^{i-1}j\)。

第 \(i,i+2,i+4\cdots\) 行的和:\(a_i \times cnt_i + 2m \times c_i \times s(cnt_i)\)

第 \(i+1,i+3\cdots\) 行的和:\(a_{i+1}\times cnt_{i+1} + 2m \times c_{i+1} \times s(cnt_{i+1})\)

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;

const int p = 998244353;

int n, m;

ll s1(ll x) {return x * (x - 1) / 2 % p;}

pair<ll, ll> calc(ll x, ll l, ll r)
{
    if((x + l) & 1) l ++;
    if((x + r) & 1) r --;

    ll fs = (x - 1) * m % p;
    ll len = (r - l + 2) / 2;
    
    return {((fs + l + fs + r) * len / 2) % p, len};
}

signed main()
{
    ios::sync_with_stdio(0);cin.tie(0);
    cin >> n >> m;

    int q; cin >> q;
    while(q --)
    {
        int x, y, u, v; 
        cin >> x >> u >> y >> v;
        
        auto t1 = calc(x, y, v);
        auto t2 = calc(x + 1, y, v);

        int l1 = (u - x + 2) / 2, l2 = u - x + 1 - l1;
        
        ll ans = 0;
        ans += t1.first * l1 + m * 2 * t1.second % p * s1(l1);
        ans += t2.first * l2 + m * 2 * t2.second % p * s1(l2);
        
        cout << ans % p << "\n";
    }

    return 0;
}

或者考虑容斥,令 \(f(x,y)=\sum_{i=1}^x\sum_{j=1}^y((i-1)m+j)[(i+j)\bmod 2=0]\)。

令 \(S(i)=\dfrac{(i+1)i}2\),也就是等差数列和。

令 \(S'(i)\) 为去掉偶数项的 \(S(i)\) 的和。

考虑化简式子:

\[\begin{aligned} f(x,y)&=\sum_{i=1}^x\sum_{j=1}^y((i-1)m+j)[(i+j)\bmod 2=0] \\ &=\sum_{i=1}^x\sum_{j=1}^y(i-1)m[(i+j)\bmod 2=0]+ \sum_{i=1}^x\sum_{j=1}^yj[(i+j)\bmod 2=0] \\ &=m\lfloor\frac {y}2\rfloor S'(x-1)+ m\lfloor\frac{y+1}2\rfloor (S(x-1)-S'(x-1))+ \lfloor\frac {x}2\rfloor (S(y)-S'(y))+ \lfloor\frac {x+1}2\rfloor S'(y) \\ \end{aligned} \]

于是答案就是

\(f(B, D)- f(A - 1, D)- f(B, C - 1)+ f(A - 1, C - 1)\)。


#include<bits/stdc++.h>
using namespace std;
typedef long long ll;

const int p = 998244353;

ll s1(ll x) {return x * (x + 1) / 2 % p;}
ll s2(ll x) {return (x + (x & 1)) * ((x + 1) / 2) / 2 % p;}

int n, m, q;

ll s(ll x, ll y)
{
    ll ans = 0;
    ans += (x / 2) % p * (s1(y) - s2(y)) + ((x + 1) / 2) % p * s2(y);
    ans += m * (y / 2) % p * s2(x - 1) + m * ((y + 1) / 2) % p * (s1(x - 1) - s2(x - 1));
    return ans % p;
}

signed main()
{
    ios::sync_with_stdio(0);cin.tie(0);
    cin >> n >> m >> q;
    while(q --)
    {
        int lx, rx, ly, ry;
        cin >> lx >> rx >> ly >> ry;
        ll ans = 0;
        ans += s(rx, ry);
        ans -= s(lx - 1, ry);
        ans -= s(rx, ly - 1);
        ans += s(lx - 1, ly - 1);
        cout << (ans % p + p) % p << "\n";
    }

    return 0;
}

标签:ll,int,题解,sum,cin,ans,ABC269F,s1
From: https://www.cnblogs.com/adam01/p/18340203

相关文章

  • ABC268F 题解
    考虑贪心。设字符串\(S\)里数字之和为\(S_d\),X的个数为\(S_c\)。考虑相邻的两个字符串\(A,B\)的贡献:考虑临项交换,这只影响到相邻两个串的相互贡献。注意到交换\(A,B\)只会影响到\(B_dA_c,A_dB_c\),那么产生的贡献\(\Delta=B_dA_c-A_dB_c\)。因为对于最优解,\(\Delta......
  • ACM第三次测试部分题解(B,C,D,E,J)
    (B)N^N(简单快速幂模板,直接套用就行)点击查看代码#include<iostream>usingnamespacestd;longlonga,b,n;intmain(){cin>>n;while(n--){scanf("%lld",&a);signedlonglongA=a%10,sum=1;while(a)......
  • AGC039B 题解
    因为一条边只能在\(V_i,V_i+1\)之间,如果把\(V_1,V_3,\cdots\)看作一部分,\(V_2,V_4,\cdots\)看作一部分,这就是个二分图。考虑一个二分图怎么“展开”成最多的集合。考虑答案上界。上界是点对最短路的最大值加一。如果集合个数超过上界,那么一定存在一条边跨越多个集合。猜......
  • AGC033C 题解
    这里树的直径\(l\)定义为两个有硬币的点的最长距离。做一次操作后,树的直径一定会变短。我们发现,如果在直径端点做操作,直径减一。在非直径端点操作,直径减二。于是变成了一个威佐夫博弈,但是要注意的是,在直径长度为0,1,2的时候,每次都只能让直径减一。因为直径长度为1,先手必......
  • AGC059B 题解
    对于一种构造,考虑怎么表示。可以把相邻不同颜色建图连边。注意到答案不可能小于\(n-1\),否则图不联通,显然不可能。考虑什么情况下是\(n-1\)。图是一棵树。考虑怎么构造出一棵树。因为一种颜色出现次数大于等于这个点的度数,可以考虑可以确定叶子。把剩余度数最小的往最大的......
  • AGC056A 题解
    首先考虑\(n\equiv0\pmod3\)的情况。非常简单,然后考虑\(n\equiv1\pmod3\)的情况。只要把多出来的第一列第一行填满就行了。还要比原来情况多一个连通块。然后考虑\(n\equiv2\pmod3\)的情况。手玩一下,再往左上角添一点东西就行了。#include<bits/stdc++.h>us......
  • AGC044B 题解
    考虑每次更新就跑一遍bfs。\(O(n^4)\),复杂度不对?但是注意到\(dis\)的最大值也就是\(n\),每次更新\(dis\)至少减一。所以最大值最多被更新\(n\)次,一共更新\(O(n^3)\)次,复杂度是对的。直接暴力。#include<bits/stdc++.h>usingnamespacestd;typedeflonglongll;......
  • ABC267F 题解
    注意到,对于一棵树\(T\)的任一直径\(a-b\),对于任意一点\(u\),离\(u\)最远的点一定是\(a\)或\(b\)。考虑反证:如图,如果存在点\(c\)使得\(dis(u,c)>\max(dis(u,a),dis(u,b))\)。如图,\(a-b\)为直径,\(d2>d1\)。因为有\(d4>d3+d2\),所以有\(d2+d3+d4>2d2+2d3>d1+d2\),所以......
  • ABC266F 题解
    输入的图是一颗基环树。对于\(x,y\),如果把环上的边去掉,得到的森林里\(x,y\)仍然在同一颗树内,那么显然只有一条路。否则一定要经过环,有两条路。于是dfs或着拓扑排序找环即可。#include<bits/stdc++.h>usingnamespacestd;typedeflonglongll;constintN=2e5+......
  • 2024集训8.2模拟赛题解
    考试历程8:30开始考试8:40快速浏览了T1并想了一下,是一道质数的题目,准备打表,打到一半的时候发现空间复杂度会爆,于是改打质数筛暴力了9:30打完T1开始看T2刚开始没思路,先看了T3,跟着样例打了一点,估计可以拿点分吧9:50打完了T3会看T2发现了一点规律(后来知道是错的)跟着思路写了一......