### Kostroma's blog

By Kostroma, 3 years ago,

Thanks bmerry for posting his solutions, we gently took some of them as a base for editorial.

Code

Problem developers: riadwaw, malcolm, Kostroma, Errichto

Code

Problem author: malcolm

Problem developers: yarrr, Edvard, malcolm, Errichto

Code

Bonus: Solve the problem, if you need to find intersection of some n - k of n rectangles, if k ≤ 10. Without data structures.

Problem author: Errichto

Problem developers: zemen, Errichto, Kostroma, riadwaw

Code

Problem author: zemen

Problem developers: yarrr, Kostroma

Code

Problem author: Errichto

Problem developers: Kostroma, malcolm

Code

Problem author: zeliboba

Code

Problem author: Kostroma

Problem developers: Kostroma, riadwaw, gchebanov, malcolm

Code

• +155

 » 3 years ago, # |   +40 It is really funny that I used totally same constructive algorithm in B task, same amount of 9 and all other digits :)
 » 3 years ago, # |   +9 How to solve C if we are asked to find any point which lies in maximum number of Rectangles?
•  » » 3 years ago, # ^ |   +27 Let's compress all values and sort points by x-coordinate. Now we can see that there is two types of events: some rectangle "opens" and some rectangle "closes". So we can solve this problem with scanline on x-axis using any data structure that can add 1 on [l, r], subtract 1 on [l, r] and tell a position of maximum value in all structure (i.e. segment tree is good for this task).
•  » » » 3 years ago, # ^ |   +3 SerezhaE how will you find the corresponding y-coordinates?
•  » » » » 3 years ago, # ^ |   +21 We have a segment tree built on y-axis, therefore for each y we know how many rectangles cover point (xcurrent, y). I think it is not hard to determine an y in which maximum value is reached  –  just start at the root of segment tree and further at every step go to the son with bigger maximum value.
•  » » 3 years ago, # ^ |   -18 I think scanline technique on x coordinate while maintaining a segment tree on y coordinate would be helpful in that case. Actually, I coded that solution during the contest, which wasted me like 30 minutes or so. XD
•  » » 3 years ago, # ^ | ← Rev. 2 →   -13 Find the intersecting segments in X and Y axis, then merge both results to get intersecting rectangle. It can be solved easily in O(n log n) using multisets: 42187139
•  » » » 3 years ago, # ^ |   0 Why so many downvotes?
 » 3 years ago, # |   +27 Some Intuition on solving Problem E:Notice that b1 = a1 mod a2, so we can write a1 = b1 + x1a2 for some non-negative integer x1.Similarly a2 = b2 + x2a3. By substituting back continuously we have a1 = b1 + x1b2 + ... + x1x2...xn - 1bn + x1x2...xna1.Hence x1x2...xn = 0 or b1 = b2 = ... = bn = 0. Also xi can be zero (i.e. ai = bi) only if bi - 1 < bi. by the definition of modulo operation. Fix some aj = bj satisfying the above condition, then generate appropriate aj - 1 and so on such that ak > bk - 1 for every k.
•  » » 3 years ago, # ^ |   +3 Very nice, thank you.
•  » » 3 years ago, # ^ |   0 I don't know how to generate aj - 1. t=b[i-j-1]-b[i-j]; t++; if(t>0){ m=t/a[i-j+1]; if(t%a[i-j+1]) m++; a[i-j]=b[i-j]+a[i-j+1]*m; } Could you tell me what do these mean？
•  » » » 3 years ago, # ^ |   +1 The condition for appropriate ak - 1 is ak - 1 > bk - 2 , i.e. bk - 1 + xk - 1ak > bk - 2 or xk - 1ak ≥ bk - 2 - bk - 1 + 1. If RHS  > 0 then xk - 1 ≥ ceil((bk - 2 - bk - 1 + 1) / ak).
•  » » » » 3 years ago, # ^ |   0 Thank you very much!!!：）
 » 3 years ago, # | ← Rev. 3 →   0 Can anybody tell me what is wrong with my solution for problem C. I have used same concept as in editorial but am getting WA on testcase 14. Solution UPD: NEVERMIND FOUND A TYPING MISTAKE
•  » » 3 years ago, # ^ |   +5 you'r algo is right.But the Problem is the way you print answer. See you'r last line in code.this one cout << p << "\n" << suf[1] << endl;
•  » » » 3 years ago, # ^ | ← Rev. 3 →   0 My code is not expected to reach there cauz if it reached there then there is not such point possible, so I put that line for debugging purpose. Also it is reaching the end in testcase 14.
 » 3 years ago, # |   +16 The code given in the editorial for problem D seemed too complicated to me. So, I got the idea from the editorial and then read vntshh's solution which was very helpful to understand it. With the help of that, I wrote a commented solution for the problem. Here is the code, if you need any help: 42211321
•  » » 3 years ago, # ^ | ← Rev. 2 →   -41 Really?
•  » » » 3 years ago, # ^ | ← Rev. 3 →   +8 You can replace the add(a, b) statements with (a + b) % mod, and it will still work. The functions are there just to avoid overuse of the % operation, as it is an expensive operation as compared to addition and subtraction. Further adding a lot of %s makes the code look messy.
•  » » » » 3 years ago, # ^ |   0 Well, maybe modulo operation is just a little bit slower than addition and substraction, but, first of all, you do c = a + b when c is ll, but a and b are ints, so you have no profit of this thing. Also, in substraction, you even didn't changed the c's type. As of mult, it's even worse. You still using the % operator (so no boost in performance) and beside that, the multiplication itself is definitely wrong and would cause an overflow on big numbers(here it probably would not, because of the constraints, but if p would be p <= 10^10 consider multiplication a pair of these). My point is, if you wanna do it — do it right, or don't at all.
•  » » » » » 3 years ago, # ^ |   0 please explain solution of problem B
•  » » » » » » 3 years ago, # ^ | ← Rev. 2 →   0 Considering the constraints of this problem, you just have to find 2 string(numbers) that alone would have max digit sums, but when added would have the minimum(1). So, a simple way to do this is just create 2 string (any way you want), when first string would be '9'*x + '0'*(x-1) + '1' and the second is just '9'*x. + is concatination, c*x is repeating x times char c. Why? Because when added they would result in '1' + '0'*(2*x-1), so the digit sum is one. X can be 1000 for example.
•  » » » » » 3 years ago, # ^ |   +5 I didn't find any better alternatives for multiplications, so using mod. It won't overflow as multiplication is left to right associative, multiplication with 1ll converts it into a long long, and later the answer modulo 1e9+7, must be an int, so I return an int. I use the sub operation when 0 <= a, b < mod. Note that a-b can not be <= -mod. So, even if it becomes negative, the absoute value of the result will never exceed mod-1, so adding mod converts the answer to a positive number. Furthermore, even if the answer is non-negative, it cannot exceed mod. I accept that in c = a + b, c must have been an int. I wrote this function some time back, and not paying much attention to whether 2*(mod-1) (which is the max. value of a + b) will fit into an int or not, I took the result into a long long variable, but yes int will probably do in that case. So, Sorry for that.
•  » » » » » » 3 years ago, # ^ |   -29 Yes, multiplication wont overflow considering a and b are ints. But, following today's "trends" you can see more problems involving modular arithmetics using the 64-bit ints, and then, your mult wont work. You can google for log n modular multiplication, if you are curious. Modular substraction is a hell of the problem actually, try printing -6 % 5 in C++ and Python. And both solutions are logical. Why do you even using ints, is it a try of getting performance boost? Cause I'm heard something about "slow 64-bit operations" but never seen a comparison. I've been using 64-bit ints and long doubles only and, till now, haven't experienced issues with that, instead i never think "should i put int, or long long this time?".
•  » » » 3 years ago, # ^ |   -23 Yeah, keep downvoting, show the codeforces' community actual face.
 » 3 years ago, # | ← Rev. 2 →   0 What is test 57 of problem E? My code is showing TLE on test 57 though its O(N). Here is the link to the code http://codeforces.com/contest/1028/submission/42212637
•  » » 3 years ago, # ^ |   +5 test: 2 1 2when j equal n-1,  while(i != j)  work infinitely
 » 3 years ago, # |   0 can anyone give better explanation for problem B.
•  » » 3 years ago, # ^ |   0 In problem B the idea is to maximize the s(a) and s(b) since m,n < 1150. In addition S(454545...45+5454....55)=1 which is the smallest possible number.
•  » » 3 years ago, # ^ | ← Rev. 2 →   0 You can make another two strings to solve Problem B. 44444445+55555555=100000000you can get shortest string a and b using this algorithm:if(n<=5) a='5',b='5',n=0; so s(a)>=s(n) and s(b)>= s(n) and s(a+b)=1 well less or equal to any n. else { a='5',b='5',n-=5; while(n>=4) a='4'+a,b='5'+b,n-=4; }because of when n-=4, s(a)+=4 and s(b)+=5, so it can ensure that s(n)<=s(a) and s(n)<=s(b).
 » 3 years ago, # |   0 I am getting heap buffer overflow in problem C while it runs fine on my computer. Can somebody check my code. 42215352
•  » » 3 years ago, # ^ |   0 instead of cs* tmp = (cs*)malloc(sizeof(cs*)); you should write cs* tmp = (cs*)malloc(sizeof(cs));
•  » » » 3 years ago, # ^ |   0 It works. Thanks
 » 3 years ago, # |   0 In problem D, what is the reason for adding m + 1 instead of m in the answer for the undetermined directions of remaining orders?
•  » » 3 years ago, # ^ | ← Rev. 2 →   +5 If the values of the undetermined n ADD orders are v1, v2, ... vn (in ascending order), so in one possible assignment all of them can be sell orders, or the first one is buy and the rest are sells, or the first two are buys and the rest are sells, ...... or all of them are buys. These are n+1 possible assignments.
 » 3 years ago, # |   +3 Alternative solution for problem C:Let x1, x2, and y1, y2 be the maximum two left x-coordinates and bottom y-coordinates of the rectangles, respectively. Then the answer is one of those four combinations, i.e. (x1, y1), (x1, y2), (x2, y1), (x2, y2).
•  » » 3 years ago, # ^ |   0 What's the reasoning behind it?
•  » » » 3 years ago, # ^ | ← Rev. 2 →   0 First, there's such a point (x, y) that satisfies the condition (possible answer) and its x value is the x-value of some rectangle, and likewise y-value. (*)WLOG, assume that x1 <= x2 and y1 <= y2. (These are the same values as I assumed in the above comment). Then if x < x1 or y < y1, then this point would not be in at least two rectangles, that's why it must be the case that x >= x1 and y >= y1. Combining this with (*) proves the statement.
•  » » 3 years ago, # ^ |   0 Would it? Spoiler
•  » » » 3 years ago, # ^ |   0 In this case, actually all four combinations can be the answer.
 » 3 years ago, # |   +10 The solution to the problem http://codeforces.com/contest/1028/problem/C is almost the same as that of this problem http://codeforces.com/contest/1029/problem/C cool to have two consecutive rounds with similar problems.
 » 3 years ago, # |   -6 "Bonus: Solve the problem, if you need to find intersection of some n - k of n rectangles, if k ≤ 10."I suppose it is very standard task to find a place where biggest number of rectangles intersect (no matter whether it is n-1, n-10 or 2137 for n=1e5). You simply sweep them from left to right with appropriate segment tree. It was given as a task on Polish OIG long ago which is contest for <=15 year old guys :P
•  » » 3 years ago, # ^ |   +69 Come on man, it's not interesting. Better find a solution in O(nk2).
•  » » » 3 years ago, # ^ |   +10 Seems, like the following works: Solve independent for X and Y. Every rectangle is just segment on axis X and the same for Y. Now we can easy find in O(N × log(N)) all X-es, which covered by at least n - k rectangles(now segments), there will be O(K) such x-es, after do the same for y and after that brute every such point in O(N). Is it ?
•  » » » 3 years ago, # ^ | ← Rev. 3 →   -28 Maybe it's not very interesting, but it seems like you guys missed it :D. Nevermind. Could you explain your solution? (I presume it is not solution mentioned here already 2 times since this one contains from sorting)
•  » » » » 3 years ago, # ^ |   0 Lol, of course we didn't miss it)Our approach is the following: the x-coordinate of the result will be either one of the k + 1 minimum right x-borders or one of the k + 1 maximum left borders. The same with y. So we have a solution in O(nk2), which is very easy and fast to write :)
•  » » » » » 3 years ago, # ^ |   0 can you explain for Case k = 2 ...
•  » » » » » » 3 years ago, # ^ |   0 Hint: solve problem for segments first, not for rectangles. If all segments intersect, then the leftmost right border lies inside their intersection. So if you erase any two segments, others will intersect in one of the 3 leftmost right borders anyway, if they intersect at all, because in the worst scenario you erased these two segments which had two leftmost right borders.
•  » » » 3 years ago, # ^ |   0 I actually solved problem C with this approach, for k = 2.
 » 3 years ago, # |   0 can we solve G without dp?can we say that dp(l,q)=((l+1)^q-l)
 » 3 years ago, # |   +6 In problem F, can you explain why number of points (x, y) with x^2 + y^2 = C is equal to the number of divisors of C after removing all the prime divisors of 4k+3 form?
•  » » 3 years ago, # ^ |   +27 I don't know if there's a natural bijection between divisors and positive solutions to x2 + y2 = C; but I know that both numbers are equal to where bi are the exponents in the prime factorisation of C (assuming all prime factors are of the form 4k + 1; other primes won't increase the number of solutions) (the formula is off by one if C is a square, because then there is a solution with y = 0 that is counted by ).Here's a sketch of how to derive the formula using Gaussian integers (they might seem scary, but I think the theory is also very beautiful):First, note that N(x + iy) = x2 + y2 is a multiplicative function ; that is, N(z1·z2) = N(z1)·N(z2).Second, recall that has unique factorisation; that is, any can be uniquely expressed as a product of "Gaussian primes" and a unit (one of 1, i,  - 1, and  - i). (There is the slightly annoying fact that each Gaussian prime has 4 associates including itself, but really they are the same. You can avoid this annoyance by picking your favourite among the associates and only using that one for factorisations, like how, in , you might write  - 15 = ( - 1)·3·5 instead of  - 15 = 1·( - 3)·5; we prefer 3 over  - 3.) Now since the norm is multiplicative, and units have norm 1, you can determine N(z) from the multiset of Gaussian primes in the factorisation of z. Since we want positive integer solutions, z = x + iy has to lie in the first quadrant, so we will always have 1 choice of unit for any given multiset (if C is a square, our formula also counts the solution with y = 0). So the number of solutions is the number of multisets of Gaussian primes such that the product of the norms is C.Finally, we need the classification of Gaussian primes: each Gaussian prime either has norm 2 (only one such Gaussian prime), p = 4k + 1 ( two Gaussian primes for each p), or q2 (q = 4k + 3) (only one Gaussian prime for each q). So the multisets are not too hard to count: If , with and , then the number of multisets is 0 if some cj is odd, and otherwise. (The only choice is in how to choose the primes of norm pi = 4k + 1: you need to distribute bi among two Gaussian primes, so there are bi + 1 possibilities.)Also, I guess the limits on x, y were increased. The maximal number of solutions for C ≤ 2·1129042 seems to be 196, which is achieved by C = 52·13·17·29·37·41·53 = 12882250225. However, only 172 of the solutions have both coordinates  ≤ 112904. For the record, here's a program that generates the points with unnecessary efficiency. Code#include using namespace std; #define rep(i,a,b) for(int i = a; i < (b); ++i) #define trav(x,v) for(auto &x : v) typedef long long ll; typedef vector vi; typedef pair pii; typedef complex ci; ll mexp(ll a, ll e, ll md){ ll res = 1; while(e){ if(e%2) res = res * a % md; a = a * a % md; e /= 2; } return res; } int root(int p){ while(true){ ll x = rand()%(p-3)+2; x = mexp(x, (p-1)/4, p); if(mexp(x, 2, p) == p-1) return x; } } ll norm(ci a){ return (a*conj(a)).real(); } ci quot(ci a, ci b){ ci c = a * conj(b); ll r = norm(b); return ci( round(double(c.real())/r), round(double(c.imag())/r)); } ci gcd(ci a, ci b){ while(norm(b)){ ci t = a -= b*quot(a, b); a = b; b = t; } return a; } int main(){ vi ps = {5, 13, 17, 29, 37, 41, 53}; vi es = {2, 1, 1, 1, 1, 1, 1}; ll prod = 1; rep(i,0,7) rep(_,0,es[i]) prod *= ps[i]; vector ga(7); rep(i,0,7){ ll r = root(ps[i]); ga[i] = gcd( ci(ps[i], 0), ci(r, 1) ); assert(norm(ga[i]) == ps[i]); } vector ls(1, ci(1,0)); rep(i,0,7){ vector nx; trav(w, ls) rep(k,0,es[i]+1){ ci z = w; rep(_,0,k) z = z * ga[i]; rep(_,k,es[i]) z = z * conj(ga[i]); nx.push_back(z); } ls = nx; } trav(z, ls){ ll x = z.real(), y = z.imag(); x = abs(x), y = abs(y); assert(x*x + y*y == prod); if(x > y && x <= 112904){ cout << x << ' ' << y << endl; cout << y << ' ' << x << endl; } } } 
•  » » » 3 years ago, # ^ |   +10 Wow, too much new knowledge. Thanks for your response!
 » 3 years ago, # |   +18 For bonus task C :Sweep only on x first, now one can prove that there will be at most 2*k + 1 points(while sweeping), where there are n-k rectangles above it. For each of these x sweep on y to find if there is a y that actually contains n-k rectangles.Complexity O(n*k*logn);2*k + 1 points because -> suppose I reach a x where there are n-k rectangles above on the subsequent points the number of rectangles may increase decrease or remain saim. In worst case it can form the pattern n-k, n-k+1, .. n , n-1, n-2 .. n-k.Solution : 42217561
 » 3 years ago, # |   0 For Problem C, You can use multiset to get O(n log n) with a simpler solution 42241507
•  » » 3 years ago, # ^ |   -18 1700 ms, using "n log n" solution. Let's see why. No fast input. Let's count log n operations actually. So we have 4 log n in input, so O(4*N log N). + 12 log n operations in computing intersections(notice the find() operations), so O(12*N log N). In result we have O(16*N log N). TYI, log2(10^5) ~= 17. Summing up, your constant is almost as high as log N multiplier, which means, you have almost O(N log^2 N) solution. I hope you understand that 300 ms is not that far from the TLE, so next time i suggest you to optimize your solutions.
•  » » » 3 years ago, # ^ |   0 Thank you for your details analysis !I actually find that prefix and suffix array way(editorial) harder and ugly.(Maybe it's just me)Well i added Fast IO to the same solution and got AC with 982 ms 42251111.It's still far slower that this random submission of 180 ms i picked, 42249815.But mine is much cleaner, you might agree.
•  » » » » 3 years ago, # ^ |   -13 Yeap, as for cleanness of code, definitely. As for time, of course, asymptotic is different, nothing surprising.
•  » » 3 years ago, # ^ |   0 I wrote a very similar solution during the contest but with fast input and it passed in about 900 ms. But anyway it can be optimized by keeping track only of the maximum 2 and minimum 2 of bottom left x & y and top right x & y respectively. It will be O(N).
 » 3 years ago, # |   +39 For bonus C: X, Y can't be answer if we find k rectangles such that x2[i] < X, or if there exist k rectangles such that x1[i] > X. Similarly for Y. Let's sort x2, y2 in ascending order, x1, y1 in descending order. We get that x1[k] ≤ X ≤ x2[k], y1[k] ≤ Y ≤ y2[k]. Then check all possible 4·k2 variants.Solution: 42165553.
 » 3 years ago, # |   0 I found a typo in the solution for Problem H, Before doing this for i, we need to update best array: for each val | ai and aival having dist primes in factorization and for each k≤7 relax best[k+dist] with dp[val][dist]. Then all queries with right border equal to i can be answered in O(Mans) time, where Mans≤14. We should relax best[k + dist] with dp[val][k] instead of dp[val][dist].
 » 17 months ago, # |   0 Can someone help in In Rectangle Question. I got wrong Answer. import randomn = int(input()) lst = [0 for i in range(n)]for i in range(n): lst[i] = tuple(map(int,input().split()))pre = [0 for i in range(n)] suf = [0 for i in range(n)]x1_min,y1_min,x1_max,y1_max = -float('inf'),-float('inf'),float('inf'),float('inf')for i in range(n): x1,y1,x2,y2 = lst[i] x1_min = max(x1_min,x1) x1_max = min(x1_max,x2) y1_min = max(y1_min,y1) y1_max = min(y1_max,y2) if(x1_max=2 and pre[1]==0 and suf[1]!=0): # print('case2') x = random.randint(suf[1][0],suf[1][2]) y = random.randint(suf[1][1],suf[1][3]) print(x,y)elif(n>=2 and suf[n-2]==0 and pre[n-2]!=0): # print('case3') x = random.randint(pre[n-2][0],pre[n-2][2]) y = random.randint(pre[n-2][1],pre[n-2][3]) print(x,y)else: for i in range(1,n-1): # print(*pre) # print(*suf) if(pre[i-1]!=0 and suf[i+1]!=0): x1_min = max(pre[i-1][0],suf[i+1][0]) x1_max = min(pre[i-1][2],suf[i+1][2]) y1_min = max(pre[i-1][1],suf[i+1][1]) x1_max = min(pre[i-1][3],suf[i+1][3])  x = random.randint(x1_min,x1_max) y = random.randint(y1_min,y1_max) # print(x1_min,y1_min,x1_max,y1_max) print(x,y) break