topcoder练习记
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了topcoder练习记相关的知识,希望对你有一定的参考价值。
自己做过的题太少了>_<
找一些tc的题来刷一刷吧 ^_^
SRM 600 div1 hard LotsOfLines
有 y = ax+b (0 <= a < A && 0 <= b < B) 这样 A*B 条直线, 问你最终这些直线把平面分成了几部分。
考虑以a为第一关键字b为第二关键字给直线排序然后一条一条地加进去并计算贡献, 显然每一条边加进去的时候就是它和原图的交点个数+1, 因为a相同的两条直线必然没有交点, 所以可以把当前的图理解成这样 : y = cx+d(0 <= c < a && 0 <= d < B) , 他们的交点个数就是 x = (d-b)/(a-c) 有多少种取值, 即 x = (-b ~ B-b-1) / (1 ~ a) 有多少种取值, 发现分子和分母都是 < A 的且始终是自然数上的一个前缀, 于是 A^2 预处理一下就可以了。 判断 a/b 有没有在前面出现过可以直接用gcd, 不存在 c/d (0 <= c < a && 0 <= c < b) 且 c/d == a/b 当且仅当 gcd(a, b) == 1 (显然)。
#include <iostream> #include <cstdio> #include <cstring> #include <cmath> #include <algorithm> #define MAXN 1205 #define ll long long using namespace std; class LotsOfLines{ public: int f[MAXN][MAXN]; ll ans; int gcd(int a, int b){return b == 0 ? a : gcd(b, a%b);} ll countDivisions(int A, int B){ for(int i = 1; i < A; i ++) for(int j = 1; j < B; j ++) f[i][j] = f[i][j-1] + f[i-1][j] - f[i-1][j-1] + (gcd(i,j)==1 ? 1 : 0); for(int i = 1; i < A; i ++) for(int j = 0; j < B; j ++){ ans += (f[i][j] + f[i][B-j-1] + 1); } return ans + (ll)A*B + 1; } };
以上是关于topcoder练习记的主要内容,如果未能解决你的问题,请参考以下文章
Atom编辑器折腾记_(15)JS代码片段补全(插件:javascript-snippets)
@topcoder - SRM603D1L3@ SumOfArrays