#include <bits/stdc++.h>
#define ll long long
#define debug if(0)
const int MAX_N = 2e5;
std::vector<std::string> t;
int n;
int c[MAX_N+3];
int original[MAX_N+3];
void input(){
std::cin >> n;
std::string s;
for (int i = 1; i <= n; i++){
std::cin >> s;
t.push_back(s);
original[i-1] = s.length();
}
}
int check(std::string &s1, std::string &s2){
for (int i = 0; i < s2.length(); i++){
if (s1[i] > s2[i])
return 0;
else if (s1[i] < s2[i])
return 1;
}
return 2;
}
std::string add(std::string s){
int it = s.length()-1;
while (it >= 0 && s[it] == '9'){
s[it] = '0';
it--;
}
if (it < 0) // same 9
return "a";
else
s[it]++;
return s;
}
int main(){
std::ios_base::sync_with_stdio(0); std::cin.tie(NULL);
input();
c[0] = t.front().length();
for (int i = 1; i < t.size(); i++){
if (t[i].length() > c[i-1])
c[i] = t[i].length();
else if (t[i].length() == c[i-1] && t[i] == t[i-1]){
c[i] = c[i-1]+1;
t[i] += '0';
}
else{
// tutaj nie moga byc rowne oraz |L| >= |R|
int stan = check(t[i-1], t[i]);
// 0 jesli L > R leksykograficznie, wtedy nowy rzad z nowymi zerami
// 1 jesli L < R leksykograficznie, wtedy ten sam rzad z nowymi zerami
// 2 jest R zawiera sie w L, tutaj trzeba ifowac
if (stan == 0){
// L > R
c[i] = c[i-1]+1;
while (t[i].length() < std::min(20, c[i]))
t[i] += '0';
}
else if (stan == 1){
// L < R
c[i] = c[i-1];
while (t[i].length() < std::min(20, c[i]))
t[i] += '0';
}
else{
// R zawiera sie w L
std::string copy = add(t[i-1]); // dodaje 1 do t[i-1]
if (check(copy, t[i]) == 2){ // jesli t[i] zawiera sie w t[i-1]+1
// wykona sie jesli do t[i-1] mozna dodac 1 tak, by rzad pozostał ten sam na miejscu znaczacym wzgledem t[i]
t[i] = copy;
c[i] = c[i-1];
}
else{
// tutaj robimy nowy rzad, trudno
c[i] = c[i-1]+1;
while (t[i].length() < std::min(20, c[i]))
t[i] += '0';
}
}
}
}
ll res = 0;
for (int i = 0; i < n; i++)
res += (ll)(c[i] - original[i]);
std::cout << res << "\n";
}
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 | #include <bits/stdc++.h> #define ll long long #define debug if(0) const int MAX_N = 2e5; std::vector<std::string> t; int n; int c[MAX_N+3]; int original[MAX_N+3]; void input(){ std::cin >> n; std::string s; for (int i = 1; i <= n; i++){ std::cin >> s; t.push_back(s); original[i-1] = s.length(); } } int check(std::string &s1, std::string &s2){ for (int i = 0; i < s2.length(); i++){ if (s1[i] > s2[i]) return 0; else if (s1[i] < s2[i]) return 1; } return 2; } std::string add(std::string s){ int it = s.length()-1; while (it >= 0 && s[it] == '9'){ s[it] = '0'; it--; } if (it < 0) // same 9 return "a"; else s[it]++; return s; } int main(){ std::ios_base::sync_with_stdio(0); std::cin.tie(NULL); input(); c[0] = t.front().length(); for (int i = 1; i < t.size(); i++){ if (t[i].length() > c[i-1]) c[i] = t[i].length(); else if (t[i].length() == c[i-1] && t[i] == t[i-1]){ c[i] = c[i-1]+1; t[i] += '0'; } else{ // tutaj nie moga byc rowne oraz |L| >= |R| int stan = check(t[i-1], t[i]); // 0 jesli L > R leksykograficznie, wtedy nowy rzad z nowymi zerami // 1 jesli L < R leksykograficznie, wtedy ten sam rzad z nowymi zerami // 2 jest R zawiera sie w L, tutaj trzeba ifowac if (stan == 0){ // L > R c[i] = c[i-1]+1; while (t[i].length() < std::min(20, c[i])) t[i] += '0'; } else if (stan == 1){ // L < R c[i] = c[i-1]; while (t[i].length() < std::min(20, c[i])) t[i] += '0'; } else{ // R zawiera sie w L std::string copy = add(t[i-1]); // dodaje 1 do t[i-1] if (check(copy, t[i]) == 2){ // jesli t[i] zawiera sie w t[i-1]+1 // wykona sie jesli do t[i-1] mozna dodac 1 tak, by rzad pozostał ten sam na miejscu znaczacym wzgledem t[i] t[i] = copy; c[i] = c[i-1]; } else{ // tutaj robimy nowy rzad, trudno c[i] = c[i-1]+1; while (t[i].length() < std::min(20, c[i])) t[i] += '0'; } } } } ll res = 0; for (int i = 0; i < n; i++) res += (ll)(c[i] - original[i]); std::cout << res << "\n"; } |
English