0
点赞
收藏
分享

微信扫一扫

逆序对的个数

沐之轻语 2022-04-05 阅读 87
c++算法

求解逆序对的个数关键在于利用分治法,将数组分成三段,分别求解在左半段内部的逆序对个数和右半段逆序对的个数,最后,在左半端和右半段排序完成后,两边合二为一的时候又有多少逆序对,解决思想与归并排序相同,只不过要加上计算逆序对的步骤。

#include<iostream>
using namespace std;
typedef long long LL;
const int maxn = 1e6 + 5;
int num[maxn];
int t[maxn];
LL merge_sort(int l, int r)
{
	if (l == r)
	{
		return 0;
	}
	else
	{
		LL ans = 0;
		int mid = (l + r) >> 1;
		ans += merge_sort(l, mid), ans += merge_sort(mid + 1, r);
		int i = l, j = mid + 1, k = 0;;
		while (i <= mid && j <= r)
		{
			if (num[i] <= num[j])
			{
				t[k++] = num[i++];
			}
			else
			{
				t[k++] = num[j++];
				ans += mid - i + 1;//在左右两边都已经排序完成的情况下,对
//于下标为i的数,i-->mid这段区间的数一定都比下标为j的数大,那么这些数一定可
//以与j形成逆序对.
			}
		}
		while (i <= mid)t[k++] = num[i++];
		while (j <= r)t[k++] = num[j++];
		for (int i = l, j = 0; i <= r; i++, j++)
		{
			num[i] = t[j];
		}
		return ans;
	}
}
int main(void)
{
	int n;
	scanf("%d", &n);
	for (int i = 0; i < n; i++)
	{
		scanf("%d", &num[i]);
	}
	printf("%lld", merge_sort(0, n - 1));
	return 0;
}
举报

相关推荐

0 条评论