BZOJ 3289 莫隊演算法 樹狀陣列

2021-07-11 11:51:57 字數 2171 閱讀 6198

time limit: 40 sec  

memory limit: 128 mb

submit: 1671  

solved: 732 [

submit][

status][

discuss]

mato同學從各路神犇以各種方式(你們懂的)收集了許多資料,這些資料一共有n份,每份有乙個大小和乙個編號。為了防止他人偷拷,這些資料都是加密過的,只能用mato自己寫的程式才能訪問。mato每天隨機選乙個區間[l,r],他今天就看編號在此區間內的這些資料。mato有乙個習慣,他總是從檔案大小從小到大看資料。他先把要看的檔案按編號順序依次拷貝出來,再用他寫的排序程式給檔案大小排序。排序程式可以在1單位時間內交換2個相鄰的檔案(因為加密需要,不能隨機訪問)。mato想要使檔案交換次數最小,你能告訴他每天需要交換多少次嗎?

第一行乙個正整數n,表示mato的資料份數。

第二行由空格隔開的n個正整數,第i個表示編號為i的資料的大小。

第三行乙個正整數q,表示mato會看幾天資料。

之後q行每行兩個正整數l、r,表示mato這天看[l,r]區間的檔案。

q行,每行乙個正整數,表示mato這天需要交換的次數。 4

1 4 2 3

21 2

2 40

2hint

n,q <= 50000

樣例解釋:第一天,mato不需要交換

第二天,mato可以把2號交換2次移到最後。

對於已有的區間可以用乙個樹狀陣列維護數字的個數,然後增加乙個數或者減少乙個

需要統計下區間裡面比他大的數字個數。注意在區間r和l改變是有區別的,不過因為

有相同的數字可以通過區間長度減去比他大的數得出比他小的個數。

複雜度(n*lgn*sqrt(n))。

坑:需要離散化。

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

#define maxn 51111

#define mod 1000000007

int pos[maxn];

int n, m;

long long c[maxn];

long long ans[maxn], tmp[maxn];

struct node

long long ans;

} p[maxn];

struct data

} a[maxn];

long long cur;

int lowbit (int x)

int r, l;

void add (int pos, int op)

void del (int pos, int op)

bool cmp (const data &a, const data &b)

int main ()

sort (a+1, a+1+n);

for (int i = 1; i <= n; i++)

sort (a+1, a+1+n, cmp);

int block = ceil (sqrt (n*1.0));

for (int i = 1; i <= n; i++) pos[i] = (i-1)/block;

scanf ("%d", &m);

for (int i = 0; i < m; i++)

sort (p, p+m);

l = 1, r = 1;

cur = 0;

memset (c, 0, sizeof c);

add (1, 1);

cur = 0;

for (int i = 0; i < m; i++)

while (r < p[i].r)

while (l > p[i].l)

while (l < p[i].l)

ans[p[i].id] = cur;

}for (int i = 0; i < m; i++)

}return 0;

}

BZOJ 3289 莫隊 樹狀陣列

題意 問 l,r 區間最少交換幾次相鄰數字使得整個序列有序。思路 統計逆序對,用樹狀陣列。然後跑一遍莫隊。離散化部分容易超時,所以直接修改了陣列。原始碼 include include include include include include include include include u...

bzoj3289(莫隊 樹狀陣列)

description mato同學從各路神犇以各種方式 你們懂的 收集了許多資料,這些資料一共有n份,每份有乙個大小和乙個編號 為了防止他人偷拷,這些資料都是加密過的,只能用mato自己寫的程式才能訪問。mato每天隨機選乙個區間 l,r 他今天就看編號在此區間內的這些資料。mato有乙個習慣,他...

BZOJ 3289 Mato的檔案管理 莫隊演算法

詢問區間內逆序對的個數。區間轉移是o logn 的,加上莫隊總複雜度 o nn logn include include include using namespace std const int n 50005 int block n a n c n n unsigned x n t n stru...