F Remainder Problem
time limit per test 4 seconds
memory limit per test 512 megabytes
inputstandard input
outputstandard output
You are given an array a consisting of 500000integers (numbered from 11 to 500000). Initially all elements of a are zero.
You have to process two types of queries to this array:
1 x y — increase ax by y;
2 x y — compute ∑i∈R(x,y)ai, where R(x,y) is the set of all integers from 1 to 500000 which have remainder y modulo x.
Can you process all the queries?
Input
The first line contains one integer q (1≤q≤500000) — the number of queries.
Then q lines follow, each describing a query. The i-th line contains three integers ti, xi and yi (1≤ti≤2). If ti=1, then it is a query of the first type, 1≤xi≤500000, and −1000≤yi≤10000. If ti=2, then it it a query of the second type, 1≤xi≤500000, and 0≤yi<xi.
It is guaranteed that there will be at least one query of type 22.
Output
For each query of type 2 print one integer — the answer to it.
Example
input
5
1 3 4
2 3 0
2 4 3
1 4 -4
2 1 0
output
4
4
0
题意:此题涉及两个操作:当为1时,输入两个数x和y,就是将a[x]+y;当为2时,输入两个数x和y,要求满足x%i==y的a[i]的和为多少。
思路:由于查询次数最大为5e5次,如果单纯的查询的话肯定会超时,如果单纯的建立一个记忆化数组的话x为50万y为1000肯定会超内存,所以我们记忆化到根号下五十万之前(得出根号下50万之前的所有结果),对于之后的结果直接暴力求解。(算出来时间刚好卡在3800多ms)
PS:应定义为longlong类型
AC代码如下:
#include<iostream>
#include<cstring>
using namespace std;
const int maxn = 5e5 + 5;
//1表示a[x]+y
//2表示返回满足x%i==y的a[i]的和
typedef long long ll;
ll a[maxn];
ll a1[705][705];
int main()
{
memset(a, 0, sizeof(a));
memset(a1, 0, sizeof(a1));
int t;
cin >> t;
while (t--)
{
int flag,x, y;
cin >> flag >> x >> y;
if (flag == 1)
{
a[x] += y;
for (int i = 1; i <= 700; i++)
a1[i][x%i] += y;
}
if (flag == 2)
{
if (x <= 700)cout << a1[x][y] << endl;
else{
ll ans = 0;
//注意i每次加x
for (int i = y; i <= 500000; i += x)
ans += a[i];
cout << ans << endl;
}
}
}
return 0;
}