题目链接: codeforces-1202D.
题目描述
          
\;\;\;\;\;
构造一个数字序列
s
s
s 包含
3
3
3 种数字
‘
1
’
‘
3
’
‘
7
’
‘1’‘3’‘7’
‘1’‘3’‘7’,使其恰有
n
n
n 个
"
1337
"
"1337"
"1337" 的子串。
          
\;\;\;\;\;
问:输出任一满足要求的数字序列,长度不超过
1
0
5
10^{5}
105.
          
\;\;\;\;\;
1
≤
n
≤
1
0
9
1\leq n \leq 10^{9}
1≤n≤109.
(题解)思路
       \;\;\; 如果序列的形式为 133...337 133...337 133...337, 1 1 1 和 7 7 7 之间有 x x x 个 3 3 3,那么子串 " 1337 " "1337" "1337" 的数量为 x ∗ ( x − 1 ) 2 \frac{x*(x-1)}{2} 2x∗(x−1). 找到一个最大的 x x x 使 x ∗ ( x − 1 ) 2 < n \frac{x*(x-1)}{2} < n 2x∗(x−1)<n,可以算出 x < 45000 x < 45000 x<45000. 还需构造 n − x ∗ ( x − 1 ) 2 n - \frac{x*(x-1)}{2} n−2x∗(x−1) 个子串,只要在第二个 3 3 3 之后插入 n − x ∗ ( x − 1 ) 2 n - \frac{x*(x-1)}{2} n−2x∗(x−1) 个 7 7 7 即可,可以算得 n − x ∗ ( x − 1 ) 2 < 45000 n - \frac{x*(x-1)}{2} < 45000 n−2x∗(x−1)<45000.
       \;\;\; 时间复杂度:预处理 O ( x ) O(x) O(x), 计算 O ( 1 ) O(1) O(1),输出 O ( l e n ) O(len) O(len).
代码
/*
nero
2019-8-21 09:59:39
*/
#include <map>
#include <cmath>
#include <queue>
#include <cstdio>
#include <string>
#include <cstring>
#include <iostream>
#include <bits/stdc++.h>
using namespace std;
#define lson(u) (u<<1)
#define rson(u) (u<<1|1)
#define Pi acos(-1)
#define iINF 0x3f3f3f3f
#define lINF 0x3f3f3f3f3f3f3f
#define EPS 0.000000001
#define pii pair<int,int>
typedef long long ll;
typedef unsigned long long ull;
int Max = 0;
ll c[50000];
int main()
{
int T;
ll n;
for(ll i = 2; ;i++) {
c[i] = i * (i-1) / 2;
if(c[i] >= (1e9)) {
Max = i;
break;
}
}
scanf("%d", &T);
while(T--) {
scanf("%lld", &n);
int t = upper_bound(c+1, c+ Max + 1, n) - c;
ll x = 1, y = t-1, z = n - c[t-1];
printf("133");
for(int i = 1; i <= z; i++) printf("7");
for(int i = 1; i <= y-2; i++) printf("3");
printf("7\n");
}
return 0;
}