#include<bits/stdc++.h>
using namespace std;
const int maxn = 1e5 + 9;
int n, xa, xb, ya, yb;
pair <int,int> p[maxn];
int f[maxn];
void work()
{
cin >> n;
for(int i = 1; i <= n; ++i)
{
scanf("%d %d %d %d", &xa, &ya, &xb, &yb);
int dx = xa - xb, dy = ya - yb;
if(!dx) dy = 1;
else if(!dy) dx = 1;
else
{
if(dx < 0) dx = -dx, dy = -dy;// 为了让斜率相等的排序后是连着的
int d = __gcd(abs(dx), abs(dy));
dx /= d; dy /= d;
}
p[i] = pair<int,int> (dx, dy);
}
sort(p + 1,p + 1 + n);
for(int i = 1; i <= n; ++i) f[i] = 0;
for(int i = 1, j; i <= n; i = j)
{
for(j = i; j <= n && p[i] == p[j]; ++j);
for(int k = 1; k <= j - i; ++k) f[k]++;
}
int i = 1, j = 1;
for(; i <= n; i++)
{
while(!f[j]) j++;
f[j]--;
printf("%d\n",i - j);
}
}
int main()
{
int T;cin>>T;while(T--)
work();
return 0;
}
hdu-6979
只读题感觉题意不是特别好懂,结合样例比较好理解
这个题关键是询问区间内,是否有mi = 1 的图层。
- 如果没有,答案就是l-r之间的前缀和(当然最大不能超过255
- 如果有,答案就是最右侧的 mi = 1的图层到 r 之间的前缀和
设置一个 f 数组,存左侧离 i 最近的 mi = 1的图层的位置
输出%x 是小写字母 %X是大写字母
#include<bits/stdc++.h>
#define ll long long
using namespace std;
const int maxn = 1e5 + 9;
int r[maxn], g[maxn], b[maxn], f[maxn];
inline int ask(int a[], int l, int r)
{
int x = f[r], res;// x是左侧离r最近的mi=1的图层,没有x就=0
if(x < l) res = a[r] - a[l-1];// 区间内没有mi=1的图层
else res = a[r] - a[x-1];
return min(res, 255);
}
void work()
{
memset(f, 0, sizeof(f));
int n, q, m;
cin >> n >> q;
for(int i = 1; i <= n; ++i)
{
scanf("%d %2X %2X %2X", &m, &r[i], &g[i], &b[i]);
r[i] += r[i-1], g[i] += g[i-1], b[i] += b[i-1];
if(m == 1) f[i] = i;
else f[i] = f[i-1];
}
for(int i = 1; i <= q; ++i)
{
int x, y;
scanf("%d %d", &x, &y);
printf("%02X%02X%02X\n",ask(r,x,y),ask(g,x,y),ask(b,x,y));
// 不足位数用0补齐,没有0表示用空格补齐
}
}
int main()
{
int T;cin>>T;while(T--)
work();
return 0;
}
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
map <ll, ll> ma;
ll n, k;
ll f(ll x)// x是区间长度
{
if(ma[x]) return ma[x];
if(x <= k) return ma[x] = 1;
else return ma[x] = f(x / 2) + f(x - x / 2) + 1;
}
void work()
{
ma.clear();
cin >> n >> k;
cout << f(n) << endl;
}
int main()
{
int T;cin>>T;while(T--)
work();
return 0;
}