题目链接:http://codeforces.com/contest/1195/problem/D2
解题心得:其实就是一个算贡献,只需要看每个数字放在不同位置能为最后的答案提供多少数值就行了,复杂度大概是 O ( 10 ∗ n ) O(10*n) O(10∗n)
#include <bits/stdc++.h>
using namespace std;
const int maxn = 5e5+100;
typedef long long ll;
const int MOD = 998244353;
ll n, num[maxn], cnt[20];//cnt[i]记录数字长度为i的有多少位
void init() {
scanf("%lld", &n);
for(int i=1;i<=n;i++) {
scanf("%lld", &num[i]);
ll temp = num[i], len = 0;
while(temp) {
len++;
temp/=10;
}
cnt[len]++;
}
}
ll upper(ll now) {//将这个数字第二位从右边开始放
int len = 0, temp = now;
while(temp) {
len ++;
temp /= 10;
}
ll ans = 0, P;
for(int i=1;i<=10;i++) {
int Cnt = cnt[i];
int Now = now;
P = 10;
for(int j=1;j<=len;j++) {
int Num = Now%10;
Now /= 10;
ans = (ans + Num*P%MOD*Cnt%MOD)%MOD;
if(j < i) {
P*=100;
} else {
P*=10;
}
P %= MOD;
}
}
return ans;
}
ll down(ll now) {//将这个数组首先从右边开始放
int len = 0, temp = now;
while(temp) {
len ++;
temp /= 10;
}
ll ans = 0, P;
for(int i=1;i<=10;i++) {
int Cnt = cnt[i];
int Now = now;
P = 1;
for(int j=1;j<=len;j++) {
int Num = Now%10;
Now /= 10;
ans = (ans + Num*P % MOD*Cnt %MOD) % MOD;
if(j <= i) {
P*=100;
} else {
P*=10;
}
P %= MOD;
}
}
return ans;
}
int main() {
// freopen("1.in.txt", "r", stdin);
init();
ll ans = 0;
for(int i=1;i<=n;i++) {
ll now = num[i];
ans = (ans + upper(now)) % MOD;
ans = (ans + down(now)) % MOD;
ll len = 0;
while(now) {
now /= 10;
len++;
}
}
printf("%lld\n", ans);
return 0;
}