二路歸併 樹狀陣列 求解逆序對

2021-08-13 22:15:02 字數 1191 閱讀 1575

常用的兩種方法,二路歸併、樹狀陣列。

二路歸併求解逆序對

二路歸併是乙個十分完美的求逆序對的方法

假設當前求到這一步,現在比較a[i],a[j]的大小,我們根據圖知道,i<=mid< j,而且第一列有序(從小到大),第二列有序,當a[i]>a[j],說明a[i]到a[mid]都大於a[j],ans+=mid-i+1。

**如下(求解n個數的逆序對個數):

#include

#include

#include

#include

using

namespace

std;

const

int tt=12345;

int n,a[100005],ans,c[100005];

int read()

while(ch>='0'&&ch<='9') ret=ret*10+ch-48,ch=getchar();

return ret*f;

}int msort(int l,int r)

}int main()

樹狀陣列求解逆序對樹狀陣列是可以快速求出前i個數的加和,那我們就可以定義f[i]表示它前面有多少個比它大的數。定義完,就想到了排序,從大到小放a[i],在a[i]初始所在的位置上放個1上去,然後每次取出的就是前面比a[i]大的數的個數。(如果理解樹狀陣列的原理,那麼這個也不難理解)

**如下:

#include

#include

using

namespace

std;

int n,f[40005],ans;

struct xcw

}a[40005];

int read()

void put(int p,int x)

int get(int p)

int main();

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

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

printf("%d\n",ans);

return

0;}

逆序對(樹狀陣列 歸併)

題目描述 貓貓tom和小老鼠jerry最近又較量上了,但是畢竟都是成年人,他們已經不喜歡再玩那種你追我趕的遊戲,現在他們喜歡玩統計。最近,tom老貓查閱到乙個人類稱之為 逆序對 的東西,這東西是這樣定義的 對於給定的一段正整數序列,逆序對就是序列中i小於j同時ai大於aj的有序對。知道這概念後,他們...

二路歸併排序(過程中求逆序對)

給定乙個1 n的排列a1,a2,an,如果ai和aj滿足i j且ai aj,我們就稱 ai,aj 是乙個逆序對。求a1,a2 an中所有逆序對的數目。input 第一行包含乙個整數n。第二行包含n個兩兩不同整數a1,a2,an。1 ai n 對於60 的資料 1 n 1000 對於100 的資料 1...

逆序對 (樹狀陣列 歸併排序

陣列前面的乙個元素 大於等於 後面的乙個元素就是乙個逆序對 樹狀陣列可以快速求字首和,利用這一特性,可以求逆序對個數,見下 用陣列c i 記錄陣列a n 中i這一元素出現的次數 當a n 中元素較大時可以離散化處理。將a n 從a n 1 到a 0 依次存到樹狀陣列中,每存乙個,對存的元素i求一次c...