hdu4768Flyer 二分

来源:互联网 发布:js object 遍历 值 编辑:程序博客网 时间:2024/04/27 12:21
//给出n个社团,每个社团对于//可以对编号为ai , ai+ci , ai + 2ci + ...ai+kci(ai+k*ci<=bi<ai+k*ci+ci)//发传单,最多有一个编号的同学受到的个数为奇数,如果有,找出这个同学//对于每一个区间,可以o(n)找出在这个区间的所有数的和,可以用二分找出//长度为1的和为奇数的区间#include<cstdio>#include<cstring>#include<iostream>using namespace std ;const int maxn = 2e4+10;typedef unsigned int ll ;ll a[maxn] , b[maxn] , c[maxn] ;ll n ;ll getsum(ll mid){    ll sum  = 0 ;    for(int i = 1;i <= n;i++)    {        ll tmp = min(b[i] , mid) ;        if(a[i] <= tmp)        sum += ((tmp-a[i])/c[i] + 1) ;    }    return sum ;}ll find(ll l , ll r){    while(l < r)    {        ll mid = (l + r) >> 1 ;        ll tmp = getsum(r) - getsum(mid) ;        if(tmp%2 == 1)        l = mid + 1 ;        else r = mid ;    }    return l ;}int main(){    while(cin>>n)    {        ll ma = 0 ;        for(int i = 1;i <= n;i++)        cin>>a[i]>>b[i]>>c[i] , ma = max(ma , b[i]) ;        ll tmp = getsum(ma) - getsum(0) ;        if(tmp%2==0)        puts("DC Qiang is unhappy.") ;        else        {            int pos = find(1 , ma) ;            cout<<pos<<" "<<getsum(pos) - getsum(pos-1)<<endl;        }    }    return 0 ;}
0 0