【2015廣東工業大學新生賽G】【區間統計 左右端點計數思想】我是好人2 區間範圍有多少個數 模x餘y
阿新 • • 發佈:2019-02-02
#include<stdio.h> #include<iostream> #include<string.h> #include<string> #include<ctype.h> #include<math.h> #include<set> #include<map> #include<vector> #include<queue> #include<bitset> #include<algorithm> #include<time.h> using namespace std; void fre(){freopen("c://test//input.in","r",stdin);freopen("c://test//output.out","w",stdout);} #define MS(x,y) memset(x,y,sizeof(x)) #define MC(x,y) memcpy(x,y,sizeof(x)) #define MP(x,y) make_pair(x,y) #define ls o<<1 #define rs o<<1|1 typedef long long LL; typedef unsigned long long UL; typedef unsigned int UI; template <class T1,class T2>inline void gmax(T1 &a,T2 b){if(b>a)a=b;} template <class T1,class T2>inline void gmin(T1 &a,T2 b){if(b<a)a=b;} const int N=0,M=0,Z=1e9+7,ms63=1061109567; int casenum,casei; int l,r,x,y; int first(int n) { int k=n/x; return k+(k*x+y<n); } int main() { scanf("%d",&casenum); for(casei=1;casei<=casenum;++casei) { scanf("%d%d%d%d",&l,&r,&x,&y); if(l>r||x<=y)puts("0"); else { int lft=first(l); int rgt=first(r+1); printf("%d\n",rgt-lft); } } return 0; } /* 【trick&&吐槽】 對於資料的特判很有必要哦。 可能l>r,可能x<=y,都對應著非法情況需要輸出0.特判掉就能AC啦! 【題意】 求區間範圍在[l,r]內,有多少個數%x==y。 l,r,x,y都是[1,1e9]範圍的數。 【型別】 區間統計,左右端點計數思想 【分析】 這種區間詢問個數的問題,都有一種很有效的做法。 找到>=左區間的第一個數,是第一個合法的 找到>右區間的第一個數,是第一個非法的 兩者下標一減就是答案。 而如果找>=n的第一個數呢? 利用倍數關係,倍數k=n/x,然後找到是k倍的滿足要求的數k*x+y 然後如果k*x+y<n,說明實際的第一個數是(k+1)*x+y。 就這樣找到編號就可以AC啦! 【時間複雜度&&優化】 O(T) */