原文链接: 完美数列 PAT A1085
上一篇: PAT A1038. Recover the Smallest Number (30)
下一篇: PAT A1010 Radix
链接: https://www.nowcoder.com/questionTerminal/5bed191944ce4eaa93f4bae50abc90df
来源:牛客网
给定一个正整数数列,和正整数p,设这个数列中的最大值是M,最小值是m,如果M <= m * p,则称这个数列是完美数列。
现在给定参数p和一些正整数,请你从中选择尽可能多的数构成一个完美数列。
输入描述:
输入第一行给出两个正整数N和p,其中N(<= 105)是输入的正整数的个数,p(<= 109)是给定的参数。第二行给出N个正整数,每个数 不超过109。
输出描述:
在一行中输出最多可以选择多少个数可以用它们组成一个完美数列。
输入例子:
10 8 2 3 20 4 5 1 6 7 8 9
输出例子:
8
先排序,然后用两个指针由小到大遍历
在a[i]确定的同时让a[j]尽可能的大
如果a[j]<= a[i]*p那么对于[i,j]内的任意位置k,一定有a[k]<=a[i]*p也成立,这种有序序列的性质可以使用two pointer思想
让i,j均指向第一个数,设置len表示满足条件的最大长度,直到a[j]<=a[i]*p恰好不成立为止,之后让i右移一位,并继续让j增加,直到j达到末尾,这个操作的目的在于在满足条件下始终控制ij的距离最大
#include <iostream>
#include <cstdio>
#include <algorithm>
using namespace std;
int a[100010];
int main(int argc, char *argv[])
{
long long n,p;
scanf("%lld %lld",&n,&p);
for(long long i=0;i<n;i++)
scanf("%lld",a+i);
//由小到大排序
sort(a,a+n);
// for(long long i=0;i<n;i++)
// printf("%lld ",a[i]);
long long i=0,j=0,len=0,t;
while(j<n){
t = a[i]*p;
while(j<n && a[j]<=t)
j++;
if(len<j-i)
len=j-i;
i++;
}
printf("%lld\n",len);
return 0;
}