P2678 跳石头
https://www.luogu.com.cn/problem/P2678
关键词:二分套二分,时间复杂度为logL * N * logN
1 #include<bits/stdc++.h> 2 using namespace std; 3 int ll, n, m, a[50005]; 4 int check(int p){ 5 int ret=0;//统计可以取消的石头数 6 for(int i=0; i<n+1; ){//模拟跳石头的过程 ,注意边界i<n+1 7 int val=a[i]+p;//以石头i、跳跃距离p 跳石头可以跳得的石头 8 int j=upper_bound(a, a+n+1, val)-a;//二分查找大于val的第一个值下标 9 ret+=j-i-1;//可以取消的石头数量 10 i=j;//跳之后到达的目标石头 11 } 12 return ret; 13 } 14 int main() 15 { 16 cin>>ll>>n>>m; 17 for(int i=1; i<=n; i++) 18 cin>>a[i]; 19 a[n+1]=ll; 20 int l=1, r=ll; 21 int ans=ll;//注意特判为,0个石头,移走数目为0 22 while(l<=r){ 23 int mid=(l+r)/2; 24 if(check(mid)>m){//如果以mid大小跳跃结果多余要求数,则说明mid偏大,此处不能是大于等于 25 ans=mid; 26 r=mid-1; 27 } 28 else 29 l=mid+1; 30 } 31 cout<<ans; 32 return 0; 33 }