很少用输入挂,以为不超时就好了,但是这题貌似不用过不去啊
只好拿出来用了,当个模板
原理是用getchar()读入会比用scanf快一些
int Read()
{
int x = 0, f = 1;
char ch;
ch = getchar();
while(ch<'0' || ch>'9')
{
if(ch=='-') f = -1;
ch = getchar();
}
while(ch>='0' && ch<='9')
x = x*10+ch-'0', ch = getchar();
return x*f;
}
2901: 矩阵求和
Time Limit: 20 Sec Memory Limit: 256 MBSubmit: 506 Solved: 284
[ Submit][ Status][ Discuss]
Description
给出两个n*n的矩阵,m次询问它们的积中给定子矩阵的数值和。
Input
第一行两个正整数n,m。
接下来n行,每行n个非负整数,表示第一个矩阵。
接下来n行,每行n个非负整数,表示第二个矩阵。
接下来m行,每行四个正整数a,b,c,d,表示询问第一个矩阵与第二个矩阵的积中,以第a行第b列与第c行第d列为顶点的子矩阵中的元素和。
Output
对每次询问,输出一行一个整数,表示该次询问的答案。
Sample Input
3 2
1 9 8
3 2 0
1 8 3
9 8 4
0 5 15
1 9 6
1 1 3 3
2 3 1 2
Sample Output
661
388
超好推得公式
用前缀和搞搞,不过询问过多复杂度也不低
#include<stdio.h>
#include<algorithm>
using namespace std;
int a[2005][2005], b[2005][2005], sa[2005][2005], sb[2005][2005];
int Read()
{
int x = 0, f = 1;
char ch;
ch = getchar();
while(ch<'0' || ch>'9')
{
if(ch=='-') f = -1;
ch = getchar();
}
while(ch>='0' && ch<='9')
x = x*10+ch-'0', ch = getchar();
return x*f;
}
int main(void)
{
long long ans;
int n, m, i, j, x1, x2, y1, y2;
while(scanf("%d%d", &n, &m)!=EOF)
{
for(i=1;i<=n;i++)
{
for(j=1;j<=n;j++)
{
a[i][j] = Read();
sa[i][j] = sa[i-1][j]+a[i][j];
}
}
for(i=1;i<=n;i++)
{
for(j=1;j<=n;j++)
{
b[i][j] = Read();
sb[i][j] = sb[i][j-1]+b[i][j];
}
}
while(m--)
{
x1 = Read(), y1 = Read();
x2 = Read(), y2 = Read();
if(x1>x2) swap(x1, x2);
if(y1>y2) swap(y1, y2);
ans = 0;
for(i=1;i<=n;i++)
ans += (long long)(sa[x2][i]-sa[x1-1][i])*(sb[i][y2]-sb[i][y1-1]);
printf("%lld\n", ans);
}
}
return 0;
}