程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> C語言 >> C++ >> C++入門知識 >> Codeforces 85D Sum of Medians(線段樹)

Codeforces 85D Sum of Medians(線段樹)

編輯:C++入門知識

Codeforces 85D Sum of Medians(線段樹)


85D Sum of Medians

題目鏈接

題意:一個集合有添加,刪除元素,每次查詢輸出集合位置為i % 5 == 3的位置和

思路:線段樹,線段樹記錄下% 5 == 0, 1, 2, 3, 4的和,並且記錄一個mov表示右移多少,每次添加一個值的時候,就當前位置之後的一整段位置都要右移一個單位,這樣去搞線段樹維護一下即可

代碼:

#include 
#include 
#include 
#include 
using namespace std;

const int N = 100005;
typedef long long ll;

int n;
char str[10];
int op[N], opx[N];

struct Hash {
	int val, rank, id;
} hash[N];
int hn;

bool cmp(Hash a, Hash b) {
	return a.val < b.val;
}

#define lson(x) ((x<<1)+1)
#define rson(x) ((x<<1)+2)

struct Node {
	int l, r, mov;
 	ll k[5];
} node[N * 4];

void pushup(int x) {
	if (node[x].l == node[x].r) {
		ll tmp = 0;
		for (int i = 0; i < 5; i++) if (node[x].k[i]) tmp = node[x].k[i];
		if (tmp == 0) return;
		memset(node[x].k, 0, sizeof(node[x].k));
		node[x].k[node[x].mov % 5] = tmp;
		return;
 	}
	for (int i = 0; i < 5; i++)
		node[x].k[(i + node[x].mov) % 5] = node[lson(x)].k[i] + node[rson(x)].k[i];
}

void build(int l, int r, int x = 0) {
	node[x].l = l; node[x].r = r;
	node[x].mov = 0;
	memset(node[x].k, 0, sizeof(node[x].k));
	if (l == r) return;
	int mid = (l + r) / 2;
	build(l, mid, lson(x));
	build(mid + 1, r, rson(x));
}

void add(int l, int r, int v, int x = 0) {
	if (node[x].l >= l && node[x].r <= r) {
		node[x].mov += v;
		pushup(x);
		return;
 	}
 	int mid = (node[x].l + node[x].r) / 2;
 	if (l <= mid) add(l, r, v, lson(x));
 	if (r > mid) add(l, r, v, rson(x));
 	pushup(x);
}

int to[N];

void add2(int v, int val, int x = 0) {
	if (node[x].l == node[x].r) {
 		memset(node[x].k, 0, sizeof(node[x].k));
		if (val == 1)
  			node[x].k[node[x].mov % 5] = to[node[x].l];
		return;
 	}
	int mid = (node[x].l + node[x].r) / 2;
	if (v <= mid) add2(v, val, lson(x));
	if (v > mid) add2(v, val, rson(x));
	pushup(x);
}

int main() {
	hn = 0;
	scanf("%d", &n);
 	for (int i = 0; i < n; i++) {
	 	scanf("%s", str);
	 	if (str[0] == 'a' || str[0] == 'd') {
   			op[i] = 1;
   			if (str[0] == 'd') op[i] = -1;
   			scanf("%d", &opx[i]);
   			hash[hn].id = i;
   			hash[hn++].val = opx[i];
		} else op[i] = 0;
 	}
 	sort(hash, hash + hn, cmp);
 	to[0] = hash[0].val;
 	hash[0].rank = 0;
 	for (int i = 1; i < hn; i++) {
 		hash[i].rank = hash[i - 1].rank;
 		if (hash[i].val != hash[i - 1].val) {
    		hash[i].rank++;
    		to[hash[i].rank] = hash[i].val;
		}
  	}
  	build(0, hash[hn - 1].rank);
  	for (int i = 0; i < hn; i++)
  		opx[hash[i].id] = hash[i].rank;
	for (int i = 0; i < n; i++) {
		if (op[i] == 0) printf("%lld\n", node[0].k[3]);
		else {
  			add(opx[i], hash[hn - 1].rank, op[i]);
     		add2(opx[i], op[i]);
		}
 	}
	return 0;
}


  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved