TopCoder SRM 681 Div1 500 LimitedMemorySeries2

這題假得不行啊…一直感覺O(nlogn)O(nlogn)是過不了的,結果TC評測機太強了啊,1e7帶個log才200+ms就跑過去了。。所以說要有信仰啊。。。

好的其實這題就是純暴力,複雜度證明我就直接從網上粘一個過來了。。

Let’s look at the max number in the range. Then, we have a recurrence T(n) = min(a,b) + T(a) + T(b), where a+b+1=n. By the “small-to-large” principle, T(n) is O(n log n), so the answer is always small.

#include <bits/stdc++.h>
#define ll long long
#define fr(i,x,y) for(int i=x;i<=y;i++)
#define rf(i,x,y) for(int i=x;i>=y;i--)
using namespace std;
const int p=1e9+7;

template<class T> void checkmin(T &a,const T &b) { if (b<a) a=b; } 
template<class T> void checkmax(T &a,const T &b) { if (b>a) a=b; }

class LimitedMemorySeries2 {
public:
    int getSum( int n, long long x0, long long a, long long b ) ;
};

inline void Add(int &x,int y){
	x+=y;
	while(x>=p) x-=p;
}

inline ll nxt(ll x0,ll a,ll b){
	return ((x0^a)+b)&((1LL<<50)-1);
}

inline ll pre(ll x,ll a,ll b){
	return x<b?(x+(1LL<<50)-b)^a:(x-b)^a;
}

int LimitedMemorySeries2::getSum(int n, long long x0, long long a, long long b) {
    ll x=x0;
    int ans=0;ll q,w;
    for(int i=1;i<=n;i++){
    	int s=0;
    	for(q=pre(x,a,b),w=nxt(x,a,b);i-s>1&&i+s<n&&q<x&&w<x;q=pre(q,a,b),w=nxt(w,a,b)) s++;
    	//cout<<pre(x,a,b)<<' '<<x<<endl;
    	Add(ans,s);
    	x=nxt(x,a,b);
    }
    return ans;
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章