A Simple Problem with Integers(HDOJ 4267)
Problem Description
Let A1, A2, ... , AN be N elements. You need to deal with two kinds of operations. One type of operation is to add a given number to a few numbers in a given interval. The other is to query the value of some element.
Input
There are a lot of test cases.
The first line contains an integer N. (1 <= N <= 50000)
The second line contains N numbers which are the initial values of A1, A2, ... , AN. (-10,000,000 <= the initial value of Ai <= 10,000,000)
The third line contains an integer Q. (1 <= Q <= 50000)
Each of the following Q lines represents an operation.
"1 a b k c" means adding c to each of Ai which satisfies a <= i <= b and (i - a) % k == 0. (1 <= a <= b <= N, 1 <= k <= 10, -1,000 <= c <= 1,000)
"2 a" means querying the value of Aa. (1 <= a <= N)
Output
For each test case, output several lines to answer all query operations.
Sample Input
4 1 1 1 1 14 2 1 2 2 2 3 2 4 1 2 3 1 2 2 1 2 2 2 3 2 4 1 1 4 2 1 2 1 2 2 2 3 2 4
Sample Output
1 1 1 1 1 3 3 1 2 3 4 1
My code
这题数据很强,没处理好就是TLE或MLE。
#include
#include
#define maxn 50005
using namespace std;
struct node
{
int v[55]; //k属于[1,10],有十种情况,a%k属于[0,k-1],有k种情况,总共11*10/2=55种情况
int l; //二维数组可能MLE,所以用一维
int r;
} tree[maxn << 2];
int a[maxn];
int n;
void build_tree(int l, int r, int id)
{
tree[id].l = l;
tree[id].r = r;
memset(tree[id].v, 0, sizeof(tree[id].v));
if (l == r)
return;
int m = (l + r) >> 1;
build_tree(l, m, id << 1);
build_tree(m + 1, r, id << 1 | 1);
}
void update(int l, int r, int id, int u, int k, int v)
{
if (l <= tree[id].l && tree[id].r <= r)
{
int t = k * (k - 1) / 2 + u; //计算出k==k,a%k==u是第几种情况
tree[id].v[t] += v;
return;
}
int m = (tree[id].l + tree[id].r) >> 1;
if (l <= m)
update(l, r, id << 1, u, k, v);
if (r > m)
update(l, r, id << 1 | 1, u, k, v);
}
int query(int x, int id)
{
if (tree[id].l > x || tree[id].r < x)
return 0;
int ans = 0;
for (int i = 1; i <= 10; i++)
{
int t = i * (i - 1) / 2 + x % i; //(i-a)%k==0 等价于i%k==a%k,把符合要求的都加上
if (tree[id].v[t])
ans += tree[id].v[t];
}
if (tree[id].l == tree[id].r)
return ans;
int m = (tree[id].l + tree[id].r) >> 1;
return ans + query(x, id << 1) + query(x, id << 1 | 1);
}
int main()
{
while (~scanf("%d", &n))
{
for (int i = 1; i <= n; i++)
scanf("%d", &a[i]); //数据量很大,要scanf
build_tree(1, n, 1);
int q;
scanf("%d", &q);
for (int i = 0; i < q; i++)
{
int d;
scanf("%d", &d);
if (d == 1)
{
int l, r, k, c;
scanf("%d%d%d%d", &l, &r, &k, &c);
update(l, r, 1, l % k, k, c);
}
else
{
int x;
scanf("%d", &x);
printf("%d
", query(x, 1) + a[x]);
}
}
}
return 0;
}