51nod 模拟3

A.二分答案即可
B.设\(fi\)走到下一格的期望步数
第一种做法是
\(fi = 1 + (1-p) (1 + f_{i-1}) + (1-p)^2(1 + f_{i-1}) + ... + (1 -p)^{...}(1 + f_{i-1})\)
右侧式子是一个收敛的等比数列
于是
\(fi = 1 + \frac{1-p}{p}(f_i+1)\)
第二种做法
\(fi = 1 +(1-p)(1 + f_{i-1} + f_i)\)
解方程可以得到上式
C.等差数列好处理,等比数列由于乘法分配率, 首项可以直接相加,Fibo数列可以求出首项和首项的前一项,递推得到余项

T1
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const ll INF = 0x3f3f3f3f3f3f3f3f;
const int N = 1e5+10;
struct mount{
	ll a, b;
	bool operator <(const mount& rhs)const{
		return make_tuple(a, -b) < make_tuple(rhs.a, -rhs.b);
	}
}mou[N], arr[N];
int n, m;
bool check(ll mid){
	ll now = arr[1].a;
	ll cur = 1;
	for(int i = 2; i <= n; ++i){
		if(arr[cur].b >= now + mid){
			now = now + mid;
		}else{
			do{
				++cur;
				if(cur > m) return false;
				if(now + mid <= arr[cur].a) {
					now = arr[cur].a;
					break;
				}else{
					if(now + mid <= arr[cur].b){
						now = now + mid;
						break;
					}
				}
			}while(1);
		}
	}
	return true;
}
int main(){
	ios::sync_with_stdio(false), cin.tie(0), cout.tie(0);
	cin >> n >> m;
	ll lo = INF, hi = -INF;
	for(int i = 1; i <= m; ++i){
		ll a, b; cin >> a >>b;
		mou[i] = {a, b};
	}
	sort(mou + 1, mou + 1 + m);
	int tot = 0;
	arr[++tot] = mou[1];
	for(int i = 2; i <= m; ++i){
		if(arr[tot].b >= mou[i].b) continue;
		arr[++tot] = mou[i];
	}
	m = tot;
	for(int i = 1; i < m; ++i){
		if(arr[i].b > arr[i + 1].a) arr[i].b = arr[i + 1].a - 1;
	}
	ll l = 0, r = 1e18, res = 0;
	while(l <= r){
		ll mid = (l + r) >> 1;
		if(check(mid)){
			res = mid;
			l = mid + 1;
		}else{
			r = mid - 1;
		}
	}
	cout << res << endl;
	return 0;
}
T2
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const ll MOD = 1e9+7;
const int N = 5e5+10;
ll qpow(ll a, ll b){
	ll ret=  1;
	for(;b;b>>=1){
		if(b & 1) ret = ret * a % MOD;
		a = a * a % MOD;
	}
	return ret;
}
ll inv(ll x){
	return qpow(x, MOD-2);
}
ll f[N];
void solve(){
	ll p, k;
	cin >> k;
	ll n = 0;
	for(int i = 1; i <= k; ++i){
		int x; cin >> x; n += x - 1;
	}
	cin >> p;
	ll base = (1 - p) * inv(p)%MOD;
	base = (base+MOD)%MOD;
	f[1] = 1;
	for(int i = 2; i <= n; ++i){
		f[i] = (1 + base * (1 + f[i-1])%MOD) % MOD;
	}
	ll ans = 0;
	for(int i = 1; i <= n; ++i){
		ans = (ans + f[i])% MOD;
	}
	cout << (ans + MOD)%MOD<< endl;
}
int main(){
	ios::sync_with_stdio(false), cin.tie(0), cout.tie(0);
	int T;
	cin >> T;
	while(T--){
		solve();
	}
	return 0;
}
T3
#pragma GCC optimize(3)
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const ll MOD = 19260817;
const int N = 1e5+10, maxS = 350, maxB = 350, TR = 4 * N, L = N ;
ll qpow(ll a, ll b){
	ll ret = 1;
	for(;b;b>>=1){
		if(b & 1) ret = ret * a % MOD;
		a = a * a % MOD;
	}
	return ret;
}
ll inv(ll x){
	return qpow(x, MOD-2);
}
ll inv2 = inv(2);
ll fac[L], ifac[L];
void init_fac(int len){
	ifac[0] = fac[0] = 1;
	for(int i = 1; i <= len; ++i) fac[i] = fac[i-1] * i % MOD;
	ifac[len] = inv(fac[len]);
	for(int i = len-1; i >= 1;--i)ifac[i] = ifac[i + 1] * (i + 1 ) % MOD;
	for(int i = 1; i <= len; ++i) ifac[i] = ifac[i] * fac[i-1]% MOD;
}
ll sum_1(ll k, ll d, int x){
	assert(x >= 1);
	return (k + d * (x - 1) + k)%MOD * x%MOD * inv2 % MOD;
}
ll sum_2(ll k, ll d, int x){
	return k * (qpow(d, x) - 1) % MOD * ifac[d-1] % MOD;
}
struct t_seq1{
	struct node{
		ll sum;
		ll k, d;
	}tree[TR];
	void update(int rt, int l, int r, ll k, ll d){
		tree[rt].sum = (tree[rt].sum + sum_1(k, d, r - l + 1)) % MOD;
		tree[rt].k = (tree[rt].k + k) % MOD;
		tree[rt].d = (tree[rt].d + d) % MOD;
	}
	void push_down(int rt, int l, int r){
		int mid = (l + r) >> 1;
		if(tree[rt].k || tree[rt].d){
			update(rt<<1, l, mid, tree[rt].k, tree[rt].d);
			update(rt<<1|1, mid + 1, r, (tree[rt].k + (mid - l + 1 ) * tree[rt].d%MOD) % MOD, tree[rt].d);
			tree[rt].k = tree[rt].d = 0;
		}
	}
	void push_up(int rt){
		tree[rt].sum = (tree[rt<<1].sum + tree[rt<<1|1].sum) % MOD;
	}
	void modify(int rt, int l, int r, int s, int t, ll k, ll d){
		if(s <= l && r <= t){
			update(rt, l, r, (k + (l - s) * d) % MOD,d);
			return;
		}
		int mid = (l + r) >> 1;
		push_down(rt, l, r);
		if(s <= mid)
			modify(rt<<1, l, mid, s, t, k, d);
		if(t > mid)
			modify(rt<<1|1, mid + 1, r, s, t, k, d);
		push_up(rt);
	}
	ll query(int rt, int l, int r, int s, int t){
		if(s <= l && r <= t){
			return tree[rt].sum;
		}
		push_down(rt, l, r);
		int mid = (l + r) >> 1;
		ll ret = 0;
		if(s <= mid)
			ret = query(rt<<1, l, mid, s, t);
		if(t > mid)
			ret = (ret + query(rt<<1|1, mid + 1, r ,s, t))%MOD;
		return ret;
	}
	void prt(int rt, int l, int r){
		cerr<<rt<<" " << l <<" " << r <<" " << tree[rt].sum <<" " << tree[rt].k <<" " <<tree[rt].d << endl;
		if(l >= r) return;
		int mid = (l + r) >> 1;
		prt(rt<<1, l, mid);
		prt(rt<<1|1, mid + 1, r);
	}
}seq1;
int n, q; ll d;
struct t_seq2{
	int bel[N];
	int S, B, base;
	ll cnt[maxB];
	ll sum[maxB];
	int L[maxB], R[maxB];
	ll a[N];
	void init(){
		S = ceil(sqrt(n)), B = ceil(1.0 * n /  S);
		for(int i = 1; i <= n; ++i) bel[i] = ceil(1.0 * i / S);
		for(int i = 1; i <= B; ++i) L[i] = R[i-1] + 1, R[i] = i * S;
		R[B] = n;
		base = qpow(d, S);
	}
	void modify(int l, int r, ll k){
		if(bel[l] == bel[r]){
			for(int i = l ; i <= r; ++i){
				a[i] = (a[i] + k) % MOD;
				sum[bel[i]] = (sum[bel[i]] + k) % MOD;
				k = (k * d) % MOD;
			}
			return;
		}
		for(int i = l, b = bel[i]; i <= R[b]; ++i){
			a[i] = (a[i] + k) % MOD;
			sum[b] = (sum[b] + k) % MOD;
			k = (k * d) % MOD;
		}
		for(int i = bel[l] + 1; i <= bel[r] - 1; ++i){
			cnt[i] = (cnt[i] + k) % MOD;
			sum[i] = (sum[i] + sum_2(k, d, S)) % MOD;
			k = (k * base) %MOD;
		}
		for(int i = L[bel[r]], b = bel[r]; i <= r; ++i){
			a[i] = (a[i] + k) % MOD;
			sum[b] = (sum[b] + k) % MOD;
			k = (k * d) % MOD;
		}
	}
	void push_down(int x){
		if(cnt[x] == 0) return;
		for(int i = L[x]; i <= R[x]; ++i){
			a[i] = (a[i] + cnt[x]) % MOD;
			cnt[x] = (cnt[x] * d) % MOD;
		}
		cnt[x] = 0;
	}
	ll query(int l, int r){
		ll ret =0;
		if(bel[l] == bel[r]){
			push_down(bel[l]);
			for(int i = l; i <= r; ++i){
				ret = (ret + a[i]) % MOD;
			}
			return ret;
		}
		push_down(bel[l]);
		push_down(bel[r]);
		for(int i = l ; i <= R[bel[l]]; ++i){
			ret = (ret + a[i]);
		}
		ret %=MOD;
		for(int i = L[bel[r]]; i <= r; ++i){
			ret = (ret + a[i]);
		}
		ret %= MOD;
		for(int i = bel[l] + 1; i <= bel[r] - 1; ++i){
			ret = (ret + sum[i]);
		}
		ret %= MOD;
		return ret;
	}
}seq2;
struct t_seq3{
	ll fib[N], fsum[N];
	ll a[N];
	ll sum[maxB];
	ll cnt1[maxB], cnt2[maxB];
	int S, B;
	int bel[N], L[maxB], R[maxB];
	void init_db() {
		S = ceil(sqrt(n)), B = ceil(1.0 * n /  S);
		for(int i = 1; i <= n; ++i) bel[i] = ceil(1.0 * i / S);
		for(int i = 1; i <= B; ++i) L[i] = R[i-1] + 1, R[i] = i * S;
		R[B] = n;
	}
	void init(){
		init_db();
		fib[1] = fib[2] = 1;
		for(int i = 3; i <= n; ++i) fib[i] = (fib[i-1] + fib[i-2]) % MOD;
		for(int i = 1; i <= n; ++i) fsum[i] = (fsum[i-1] + fib[i]) % MOD;
	}
	void modify(int l, int r){
		if(bel[l] == bel[r]){
			for(int i = l; i <= r; ++i){
				a[i] = (a[i] + fib[i - l + 1]) % MOD;
				sum[bel[i]] = (sum[bel[i]] + fib[i - l + 1]) % MOD;
			}
			return;
		}
		int cur = 1;
		for(int i = l, b = bel[i]; i <= R[bel[l]]; ++i){
			a[i] = (a[i] + fib[cur])%MOD;
			sum[b] = (sum[b] + fib[cur]) % MOD;
			++cur;
		}
		for(int i = bel[l] + 1; i <= bel[r] - 1;++i){
			cnt1[i] = (cnt1[i] + fib[cur]) % MOD;
			cnt2[i] = (cnt2[i] + fib[cur-1]) % MOD;
			sum[i] = (sum[i] + (fsum[cur + S - 1] - fsum[cur-1]) % MOD) % MOD;
			cur = cur + S;
		}
		for(int i = L[bel[r]], b = bel[i] ; i <= r; ++i){
			a[i] = (a[i] + fib[cur]) % MOD;
			sum[b] = (sum[b] + fib[cur]) % MOD;
			++cur;
		}
	}
	void push_down(int x){
		ll f2 = cnt2[x], f1 = cnt1[x], f3 = (f1 + f2) % MOD;
		for(int i = L[x]; i <= R[x]; ++i){
			a[i] = (a[i] + f1)%MOD;
			f2 = f1, f1 = f3, f3 =  (f1 + f2) % MOD;
		}
		cnt1[x] = cnt2[x] = 0;
	}
	ll query(int l, int r){
		if(bel[l] == bel[r]){
			push_down(bel[l]);
			ll ret = 0;
			for(int i = l ; i <= r; ++i){
				ret = (ret + a[i]);
			}
			ret %= MOD;
			return ret;
		}
		push_down(bel[l]), push_down(bel[r]);
		ll ret = 0;
		for(int i = l; i <= R[bel[l]]; ++i){
			ret = (ret + a[i]);
		}
		ret %= MOD;
		for(int i = L[bel[r]]; i <= r; ++i){
			ret = (ret + a[i]);
		}
		ret %= MOD;
		for(int i = bel[l] + 1; i <= bel[r]- 1; ++i){
			ret = (ret + sum[i]);
		}
		ret %= MOD;
		return ret;
	}
   void prt(){
        for(int i = 1; i <= B;++i){
            cerr<<"i = " << i << " sum = " << sum[i] <<endl;
            cerr<<"lazy = ";
			cerr<<cnt1[i] <<" " << cnt2[i] << endl;
            for(int j = L[i]; j <= R[i];++j){
                cerr<< a[j] <<" ";
            }
            cerr<<endl;
        }
    }
}seq3;
struct t_seq4{
	ll sum[N];
	ll query(int l, int r){
		return (sum[r] - sum[l-1]) % MOD;
	}
	void init(){
		for(int i = 1; i <= n; ++i){
			sum[i] = (sum[i-1] + sum[i]) % MOD;
		}
	}
}seq4;
int main(){
	init_fac(1e5 + 5);
	ios::sync_with_stdio(false), cin.tie(0), cout.tie(0);
	cin >> n >> q >> d;
	for(int i = 1; i <= n; ++i){
		cin >> seq4.sum[i];
	}
	seq2.init();
	seq3.init();
	seq4.init();
	for(int i = 1; i <= q; ++i){
		int opt, l, r, k, d;
		cin >> opt >> l >> r;
		if(opt == 1){
			cin >> k >> d;
			seq1.modify(1, 1, n, l, r, k, d);
		}else if(opt == 2){
			cin >> k;
			seq2.modify(l, r, k);
		}else if(opt == 3){
			seq3.modify(l, r);
		}else{
			ll 
				ans1 = seq1.query(1 ,1 ,n, l, r), 
				ans2 = seq2.query(l, r),
				ans3 = seq3.query(l, r),
				ans4 = seq4.query(l, r);
			ll ans = (ans1 + ans2 + ans3 + ans4) % MOD;
			ans = (ans + MOD) % MOD;
			cout << ans << "\n";
		}
	}
	return 0;
}
posted @ 2022-08-20 16:17  CDsidi  阅读(27)  评论(0编辑  收藏  举报