HDU 5178 pairs【二分】||【尺取】
阿新 • • 發佈:2019-03-04
family 分析 air 運行 解釋 else 技術分享 宋體 tps
<題目鏈接>
題目大意:
給定一個整數序列,求出絕對值小於等於k的有序對個數。
解題分析:
$O(nlong(n))$的二分很好寫,這裏就不解釋了。本題尺取$O(n)$也能做,並且效率很不錯。
尺取:
#include <bits/stdc++.h> using namespace std; int arr[int(1e5+5)]; int main(){ int T,n,k;scanf("%d",&T); while(T--){ scanf("%d%d",&n,&k);尺取for(int i=1;i<=n;i++) scanf("%d",&arr[i]); sort(arr+1,arr+1+n); long long ans=0; for(int l=1,r=1;l<=n;++l){ while(r+1<=n && arr[r+1]-arr[l]<=k)r++; //因為需要判斷後面的arr[r+1]是否符合條件,從而決定r是否要右移,所以這裏用的是r+1 ans+=r-l; } printf("%lld\n",ans); } }
二分:
#include <bits/stdc++.h> using namespace std; int arr[int(1e5+5)]; int main(){ int n,k,T;scanf("%d",&T);while(T--){ scanf("%d%d",&n,&k); for(int i=1;i<=n;i++) scanf("%d",&arr[i]); sort(arr二分+1,arr+1+n); long long ans=0; for(int i=1;i<=n;i++){ int cur=arr[i]+k; int l=1,r=n; while(l<=r){ int mid=l+r>>1; if(arr[mid]<=cur)l=mid+1; //找到差值小於等於k的坐標最右的數 else r=mid-1; } ans+=l-1-i; //因為最後符合的情況是運行l=mid+1指令,所以最後答案mid的值為l-1 } printf("%lld\n",ans); } }
2019-03-04
HDU 5178 pairs【二分】||【尺取】