結果

問題 No.925 紲星 Extra
ユーザー chocoruskchocorusk
提出日時 2019-11-09 00:34:30
言語 C++14
(gcc 12.3.0 + boost 1.83.0)
結果
AC  
実行時間 9,470 ms / 10,000 ms
コード長 2,519 bytes
コンパイル時間 1,232 ms
コンパイル使用メモリ 118,308 KB
実行使用メモリ 5,376 KB
最終ジャッジ日時 2024-09-15 03:23:44
合計ジャッジ時間 65,283 ms
ジャッジサーバーID
(参考情報)
judge4 / judge1
このコードへのチャレンジ
(要ログイン)

テストケース

テストケース表示
入力 結果 実行時間
実行使用メモリ
testcase_00 AC 2 ms
5,248 KB
testcase_01 AC 2 ms
5,376 KB
testcase_02 AC 2 ms
5,376 KB
testcase_03 AC 28 ms
5,376 KB
testcase_04 AC 34 ms
5,376 KB
testcase_05 AC 3,277 ms
5,376 KB
testcase_06 AC 3,263 ms
5,376 KB
testcase_07 AC 3,280 ms
5,376 KB
testcase_08 AC 3,032 ms
5,376 KB
testcase_09 AC 2,661 ms
5,376 KB
testcase_10 AC 3,834 ms
5,376 KB
testcase_11 AC 2,946 ms
5,376 KB
testcase_12 AC 2,364 ms
5,376 KB
testcase_13 AC 2,696 ms
5,376 KB
testcase_14 AC 3,835 ms
5,376 KB
testcase_15 AC 2,480 ms
5,376 KB
testcase_16 AC 5,957 ms
5,376 KB
testcase_17 AC 9,470 ms
5,376 KB
testcase_18 AC 3,785 ms
5,376 KB
testcase_19 AC 5,007 ms
5,376 KB
testcase_20 AC 2,582 ms
5,376 KB
testcase_21 AC 1,909 ms
5,376 KB
権限があれば一括ダウンロードができます

ソースコード

diff #

#include <cstdio>
#include <cstring>
#include <iostream>
#include <string>
#include <cmath>
#include <bitset>
#include <vector>
#include <map>
#include <set>
#include <queue>
#include <deque>
#include <algorithm>
#include <complex>
#include <unordered_map>
#include <unordered_set>
#include <random>
#include <cassert>
#include <fstream>
#include <utility>
#include <functional>
#include <time.h>
#include <stack>
#include <array>
#define popcount __builtin_popcount
using namespace std;
typedef long long int ll;
typedef pair<ll, ll> P;
int n;
vector<ll> seg[500];
vector<ll> sum[500];
const int b=800;
vector<ll> a;
void update(int x, ll y){
	a[x]=y;
	int t=x/b;
	for(int i=t*b; i<min((t+1)*b, n); i++){
		seg[t][i-t*b]=a[i];
	}
	sort(seg[t].begin(), seg[t].end());
	for(int i=0; i<seg[t].size(); i++){
		sum[t][i+1]=sum[t][i]+seg[t][i];
	}
}
int count(int l, int r, ll x){
	int ret=0;
	int l1=(l+b-1)/b, r1=r/b;
	for(int i=l; i<l1*b; i++){
		if(a[i]<=x) ret++;
		if(i==r-1){
			return ret;
		}
	}
	for(int i=l1; i<r1; i++){
		ret+=upper_bound(seg[i].begin(), seg[i].end(), x)-seg[i].begin();
	}
	for(int i=r1*b; i<r; i++){
		if(a[i]<=x) ret++;
	}
	return ret;
}
ll med(int l, int r){
	ll al=0, ar=(1ll<<40);
	int m=(r-l+1)/2;
	while(ar-al>1){
		ll am=(al+ar)>>1;
		int cnt=count(l, r, am);
		if(cnt>=m) ar=am;
		else al=am;
	}
	return ar;
}
ll query(int l, int r){
	ll md=med(l, r);
	ll ret=0;
	int l1=(l+b-1)/b, r1=r/b;
	for(int i=l; i<l1*b; i++){
		if(a[i]<md) ret+=md-a[i];
		else ret+=a[i]-md;
		if(i==r-1){
			return ret;
		}
	}
	for(int i=l1; i<r1; i++){
		int k=lower_bound(seg[i].begin(), seg[i].end(), md)-seg[i].begin();
		ret+=md*k-sum[i][k];
		ret+=sum[i].back()-sum[i][k]-md*(seg[i].size()-k);
	}
	for(int i=r1*b; i<r; i++){
		if(a[i]<md) ret+=md-a[i];
		else ret+=a[i]-md;
	}
	return ret;
}
int main()
{
	int q;
	cin>>n>>q;
	a.resize(n);
	for(int i=0; i<n; i++){
		scanf("%lld", &a[i]);
		a[i]++;
		seg[i/b].push_back(a[i]);
	}
	for(int i=0; i<=(n-1)/b; i++){
		sort(seg[i].begin(), seg[i].end());
		sum[i].resize(seg[i].size()+1);
		for(int j=0; j<seg[i].size(); j++){
			sum[i][j+1]=sum[i][j]+seg[i][j];
		}
	}
	ll p1=(1<<16)-1, p2=(1ll<<40)-1;
	ll s=0;
	for(int i=0; i<q; i++){
		int t;
		scanf("%d", &t);
		if(t==1){
			int x; ll y;
			scanf("%d %lld", &x, &y);
			x^=(s&p1);
			y^=(s&p2);
			update(x-1, y+1);
		}else{
			int l, r;
			scanf("%d %d", &l, &r);
			l^=(s&p1);
			r^=(s&p1);
			if(l>r) swap(l, r);
			l--;
			ll ans=query(l, r);
			printf("%lld\n", ans);
			s^=ans;
		}
	}
	return 0;
}
0