Oracle
Total Submission(s): 222 Accepted Submission(s): 90
题意:把一个数字字符串分为两个正整数,是两部分的加和最大。
思路:
先记录 0−90-90−9这101010个数字分别有多少个。不难看出,最小的一个存在的数字和其余的数字降序排列的相加就是答案,但是最小的那个数字不能是000,因为题面上说明是正整数。将这两个数加起来时,注意处理进位问题。考虑无解的情况,即一串数字中仅存在111个非000数字或不存在。(PS.这道题目原本的时限是1s1s1s,考虑到题目的难度和评测机的问题,开了4s4s4s,大家可以自己在FST以后看一下时间。如果是时限是1s1s1s的话,sortsortsort是过不了的,输出也需要优化一下)
时间复杂度 O(Tn)O(Tn)O(Tn)。
The youngest and most beautiful is Psyche, whose admirers, neglecting the proper worship of the love goddess Venus, instead pray and make offerings to her. Her father, the king, is desperate to know about her destiny, so he comes to the Delphi Temple to ask for an oracle.
To get the meaning, he needs to rearrange the digits and split the number into <b>two positive integers without leading zeroes</b>, and their sum should be as large as possible.
Help him to work out the maximum sum. It might be impossible to do that. If so, print `Uncertain`.
For each test case, the single line contains an integer n (1≤n<1010000000) .
3 112 233 1
22 35 UncertainHintIn the first example, it is optimal to split $ 112 $ into $ 21 $ and $ 1 $, and their sum is $ 21 + 1 = 22 $. In the second example, it is optimal to split $ 233 $ into $ 2 $ and $ 33 $, and their sum is $ 2 + 33 = 35 $. In the third example, it is impossible to split single digit $ 1 $ into two parts.
#include <iostream>
#include <cstring>
#include <cstdio>
#include <algorithm>
#include <cmath>
#include <queue>
#include <stack>
#include <vector>
using namespace std;
char s[10000001];
int A[10];
int main()
{
int t;
scanf("%d",&t);
while(t--)
{
scanf("%s",s);
int cnt=0;
memset(A,0,sizeof(A));
for(int i=0; s[i]; i++)
{
if(s[i]!='0')
cnt++;
A[s[i]-'0']++;
}
if(cnt<2)
{
printf("Uncertain\n");
continue;
}
char c;
for(int i=1; i<=9; i++)
{
if(A[i]!=0)
{
c=i+'0';
A[i]--;
break;
}
}
int k=0;
for(int i=0; i<=9; i++)
{
while(A[i]--)
{
s[k++]=i+'0';
}
}
int jin=0;
int tmp=c+s[0]-'0'-'0';
s[0]=tmp%10+'0';
jin=tmp/10;
for(int i=1;i<k&&jin>0;i++)
{
tmp=jin+s[i]-'0';
s[i]=tmp%10+'0';
jin=tmp/10;
}
if(jin)
printf("1");
for(int i=k-1;i>=0;i--)
printf("%c",s[i]);
printf("\n");
}
return 0;
}
Arrange
Total Submission(s): 195 Accepted Submission(s): 71
题意:针对一个确定的数列,Bi代表A1-Ai的最小值,Ci代表A1-Ai的最大值,求符合要求的数列可以有多少个。
思路:
This has drawn the fury of his mother, Venus. The goddess then throws before Psyche a great mass of mixed crops.
There are n heaps of crops in total, numbered from 1 to n .
Psyche needs to arrange them in a certain order, assume crops on the i -th position is Ai .
She is given some information about the final order of the crops:
1. the minimum value of A1,A2,...,Ai is Bi .
2. the maximum value of A1,A2,...,Ai is Ci .
She wants to know the number of valid permutations. As this number can be large, output it modulo 998244353 .
Note that if there is no valid permutation, the answer is 0 .
For each test case, the first line of input contains single integer n (1≤n≤105) .
The second line contains n integers, the i -th integer denotes Bi (1≤Bi≤n) .
The third line contains n integers, the i -th integer denotes Ci (1≤Ci≤n) .
2 3 2 1 1 2 2 3 5 5 4 3 2 1 1 2 3 4 5
1 0HintIn the first example, there is only one valid permutation (2,1,3) . In the second example, it is obvious that there is no valid permutation.
#include <iostream>
#include <cstring>
#include <cstdio>
#include <algorithm>
#include <cmath>
#include <queue>
#include <stack>
#define LL long long
using namespace std;
const int N=1e5+10;
const int MOD=998244353;
int B[N];
int C[N];
int main()
{
int t,n;
scanf("%d",&t);
while(t--)
{
scanf("%d",&n);
for(int i=1;i<=n;i++)
scanf("%d",&B[i]);
for(int i=1;i<=n;i++)
scanf("%d",&C[i]);
LL X=B[1],M=C[1];
if(X!=M)
{
printf("0\n");
continue;
}
LL tmp=1;
int flag=1;
LL ans=1;
for(int i=2;i<=n;i++)
{
if(X>B[i]&&M<C[i]||X<B[i]||M>C[i])
{
flag=0;
break;
}
else if(X>B[i]&&M==C[i])
{
X=B[i];
tmp++;
}
else if(X==B[i]&&M<C[i])
{
M=C[i];
tmp++;
}
else
{
(ans*=(M-X+1-tmp))%=MOD;
tmp++;
}
}
if(!flag)
printf("0\n");
else
printf("%I64d\n",ans);
}
return 0;
}
Wool
Total Submission(s): 234 Accepted Submission(s): 67
题意:
黎明时,Venus为Psyche定下了第二个任务。她要渡过河,收集对岸绵羊身上的金羊毛。 那些绵羊狂野不驯,所以Psyche一直往地上丢树枝来把它们吓走。地上现在有n n n根树枝,第i i i根树枝的长度是ai a_i ai. 如果她丢的下一根树枝可以和某两根树枝形成三角形,绵羊就会被激怒而袭击她。 现在Psyche手中只有长度不小于L L L且不大于R R R的树枝。请你帮忙计算,她下一根可以丢多少种不同长度的树枝而不会把绵羊激怒呢?提示:
Provider : frank_c1
考虑三角形三条边a,b,c a,b,c a,b,c (a≥b) (a \ge b) (a≥b)的关系a−b<c,a+b>c a - b < c, a + b > c a−b<c,a+b>c,即c∈(a−b,a+b) c \in (a-b,a+b) c∈(a−b,a+b)。
令加入的边为c c c,枚举所有边作为a a a的情况。对于所有可行的b b b,显然与a a a相差最小的可以让(a−b,a+b) (a-b,a+b) (a−b,a+b)覆盖范围最大,所以可以贪心地选择不大于a a a的最大的b b b。
于是我们可以先将边按长度排序,然后ai a_i ai和ai+1 a_{i + 1} ai+1建一条线段。线段并是不合法的部分。
将所有线段按左端点排序,按序扫描一遍,过程中统计答案即可。
时间复杂度O(Tn logn) O(Tn\ \log n) O(Tn logn)。
She is to cross a river and fetch golden wool from violent sheep who graze on the other side.
The sheep are wild and tameless, so Psyche keeps on throwing sticks to keep them away.
There are n sticks on the ground, the length of the i -th stick is ai .
If the new stick she throws forms a triangle with any two sticks on the ground, the sheep will be irritated and attack her.
Psyche wants to throw a new stick whose length is within the interval [L,R] . Help her calculate the number of valid sticks she can throw next time.
For each test case, the first line of input contains single integer n,L,R (2≤n≤105,1≤L≤R≤1018) .
The second line contains n integers, the i -th integer denotes ai (1≤ai≤1018) .
2 2 1 3 1 1 4 3 10 1 1 2 4
2 5HintIn the first example, $ 2, 3 $ are available. In the second example, $ 6, 7, 8, 9, 10 $ are available.
#include <iostream>
#include <cstring>
#include <cstdio>
#include <queue>
#include <algorithm>
#include <queue>
#include <stack>
#include <cmath>
#define LL long long
using namespace std;
const int N=1e5+10;
LL A[N];
struct node
{
LL l,r;
bool operator<(const node&J)const
{
return l<J.l;
}
}que[N];
int main()
{
int t;
scanf("%d",&t);
LL L,R;
int n;
while(t--)
{
scanf("%d %lld %lld",&n,&L,&R);
for(int i=0;i<n;i++)
{
scanf("%lld",&A[i]);
}
sort(A,A+n);
int k=0;
for(int i=1;i<n;i++)
{
que[i].l=max(L,A[i]-A[i-1]+1);
que[i].r=min(R,A[i]+A[i-1]-1);
}
LL ans=R-L+1;
int i=1;
while(que[i].l>que[i].r) //去除一开始不符合条件的;
i++;
LL l=que[i].l,r=que[i].r;
LL tl,tr;
for(;i<n;i++)
{
if(que[i].l>que[i].r)
break;
else if(que[i].l<=r)
r=que[i].r;
else
{
ans-=r-l+1;
l=que[i].l;
r=que[i].r;
}
}
ans-=r-l+1;
printf("%I64d\n",ans);
}
return 0;
}