[codeforces] 1967B2. Reverse Card (Hard Version)

starbow·2024년 5월 21일

PS/CP

목록 보기
1/25

문제 링크

bgcd(a,b)b \cdot \gcd(a, b)a+ba+b로 나누어 떨어지는 (a,b)(a, b)의 갯수를 구하는 문제입니다.

gcd(a,b)=ggcd(a, b) = g일 때, 적당한 양의 정수 a,ba',\, b'에 대하여 a=ag,b=bg,gcd(a,b)=1a = a'g,\, b = b'g,\, \gcd(a', b') = 1이 성립하고

a+bbg  (a+b)gbg2  (a+b)bg  (a+b)g  (gcd(a+b,b)=1)\begin{aligned} &a+b \, \vert \, bg \\ \Leftrightarrow \; &(a'+b')g \, \vert \, b'g^2 \\ \Leftrightarrow \; &(a'+b') \, \vert \, b'g \\ \Leftrightarrow \; &(a'+b') \, \vert \, g \; (\because \gcd(a'+b', b') = 1) \end{aligned}

를 얻을 수 있습니다.

문제 조건까지 종합 해보면 a+b=da'+b' = d일 때 아래 세 조건을 만족해야 합니다.

(b+1dng+b)(dg)(gcd(d,b)=1)\left( b' + 1 \leq d \leq \lfloor \frac n g \rfloor + b' \right) \, \wedge \, \left( d \, | \, g \right) \, \wedge \, \left( \gcd(d, b') = 1 \right)

1bmg1 \leq b' \leq \lfloor \frac m g \rfloor을 만족해야 하므로 max(1,dng)bmin(d1,mg)\max(1, d - \lfloor \frac n g \rfloor) \leq b' \leq \min(d-1, \lfloor \frac m g \rfloor)가 됩니다.

즉, gcd(a,b)=ggcd(a, b) = g를 만족하는 순서쌍 (a,b)(a, b)의 갯수는 아래와 같고

dg{xgcd(d,x)=1max(1,dng)xmin(d1,mg)}\sum_{d \, | \, g}{\left\lvert\{x|\gcd(d, x) = 1 \wedge \max(1, d - \lfloor \frac n g \rfloor) \leq x \leq \min(d-1, \lfloor \frac m g \rfloor) \}\right\rvert}

문제에서 구해야 하는 순서쌍의 갯수는 아래와 같습니다.

g=1min(n,m)dg{xgcd(d,x)=1max(1,dng)xmin(d1,mg)}\displaystyle\sum_{g = 1}^{\min(n, m)}{\sum_{d \, | \, g}{\left\lvert\{x|\gcd(d, x) = 1 \wedge \max(1, d - \lfloor \frac n g \rfloor) \leq x \leq \min(d-1, \lfloor \frac m g \rfloor) \}\right\rvert}}

시그마 부분을 살짝 바꾸면 아래와 같이 바꿀 수 있습니다.

d=1min(n,m)dg{xgcd(d,x)=1max(1,dng)xmin(d1,mg)}\displaystyle\sum_{d = 1}^{\min(n, m)}{\sum_{d \, | \, g}{\left\lvert\{x|\gcd(d, x) = 1 \wedge \max(1, d - \lfloor \frac n g \rfloor) \leq x \leq \min(d-1, \lfloor \frac m g \rfloor) \}\right\rvert}}

이제 위 식의 값을 구해야 합니다. 잘 보시면 gg가 증가함에 따라 max(1,dng)\max(1, d - \lfloor \frac n g \rfloor) 는 증가하고 min(d1,mg)\min(d-1, \lfloor \frac m g \rfloor)는 감소하는 것을 알 수 있습니다. 그러면 g=dg = d일때는 gcd(d,x)=1\gcd(d, x) = 1을 만족하는 xx의 갯수를 Naive하게 구한 다음 gg가 증가함에 따라 범위에서 제외되는 값을들 확인하면서 갯수를 줄여가는 방식으로 구할 수 있습니다.

위 방법의 시간 복잡도는 아래와 같습니다. TLE를 안 받을 수 있을만큼 충분히 빠를까요?

O(log(min(n,m))d=1min(n,m)max(0,min(d1,md)max(1,dnd)))O\left(\log(\min(n, m)) \cdot \displaystyle\sum_{d = 1}^{\min(n, m)}{\max\left(0, \min(d-1, \lfloor \frac m d \rfloor)-\max(1, d - \lfloor \frac n d \rfloor)\right)}\right)

조금 더 간단하게 표현해 보겠습니다. 잘 보시면 ddnd2n \leq d^2 혹은 md2m \leq d^2을 만족하기 시작하면 min\min 혹은 max\max에 해당하는 값이 바뀌며 dm+nd \geq \sqrt{m+n}이면 min(d1,md)max(1,dnd)\min(d-1, \lfloor \frac m d \rfloor)-\max(1, d - \lfloor \frac n d \rfloor)는 0 이하가 됩니다.

즉, 시간 복잡도를 간단하게 표현하면 아래와 같이 됩니다.

O(log(m+n)(d=1max(n,m)d+d=max(n,m)+1n+m2(n+m)d))O(log(m+n)(d=1n+md+d=n+m+12(n+m)2(n+m)d))O((n+m)2log(m+n))O((n+m)log(m+n))\begin{aligned} &O\left(\log(m+n) \cdot \left(\displaystyle\sum_{d = 1}^{\max(\sqrt{n}, \sqrt{m})}{d} + \displaystyle\sum_{d=\max(\sqrt{n}, \sqrt{m})+1}^{\sqrt{n+m}}{2(\sqrt{n}+\sqrt{m})-d} \right) \right) \\\\ \rightarrow \, &O\left(\log(m+n) \cdot \left(\displaystyle\sum_{d = 1}^{\sqrt{n}+\sqrt{m}}{d} + \displaystyle\sum_{d=\sqrt{n}+\sqrt{m}+1}^{2(\sqrt{n}+\sqrt{m})}{2(\sqrt{n}+\sqrt{m})-d}\right) \right) \\\\ \rightarrow \, &O((\sqrt{n}+\sqrt{m})^2\log(m+n)) \\\\ \rightarrow \, &O((n+m)\log(m+n)) \end{aligned}

nnmm은 모든 테케를 다 합쳐도 각각 200만을 넘지 않고 제한시간은 2초이므로 충분히 빠르다는 것을 알 수 있습니다.

pseudo code는 다음과 같습니다.

ans <- 0 // answer
loop d from 1 to min(n, m) {
	cur <- 0
	loop g from d to min(n, m) step d { // g = d, 2d, 3d, ...
        if g equal d {
        	l, r <- max(1, d-n/d), min(d-1, m/d)
            cur <- number of x such that gcd(d, x) == 1 and l <= x <= r
            ans += cur
        }
        else {
        	nl, nr <- max(1, d-n/d), min(d-1, m/d)
            cur -= number of x such that gcd(d, x) == 1 and (l <= x < nl or nr < x <= r)
            ans += cur
            l, r <- nl, nr
        }
        
        if l > r {
        	break
        }
    }
}

print ans
profile
🎈 Journey of problem solving

0개의 댓글