[LeetCode]493. Reverse Pairs 深入浅出算法讲解和代码示例

1、汇总概要

本提解题思路涵盖了插入排序、二分查找、mergeSort思路。

2、题目

Given an array nums, we call (i, j) an important reverse pair if i < j and nums[i] > 2*nums[j].


You need to return the number of important reverse pairs in the given array.


Example1:


Input: [1,3,2,3,1]

Output: 2

Example2:


Input: [2,4,3,5,1]

Output: 3

Note:

The length of the given array will not exceed 50,000.

All the numbers in the input array are in the range of 32-bit integer.

3、审题

给一个序列,找出它的反转对个数。

判断反转对规则:if i < j and nums[i] > 2*nums[j].

4、解题思路

最基本的思路是双重循环遍历,时间复杂度是O(n*n),舍弃。

考虑O(nlogn)的复杂度。

1. 将列表数组分为左右两个子数组,list = [[x,x,x][x,x,x]],满足左边的数组有序,右边的数组无序;

2. 左边数组元素的index都小于右边数组的index,在遍历右边数组元素时,找到左边数组中比它大2倍的数,即是反转对。

讲到这里大家理解了,其实就是插入排序、二分查找反转对。

初始是左边数组为空,右边数组为原list,遍历右边数组中元素,依次往左边数组中插入排序,二分查找插入的位置。

该算法基本没有额外空间消耗,用的mergeSort性质。

5、代码示例 - Java

public class ReversePairs {
	public int midSearch(int[] list,int low,int high, int value) throws InterruptedException{
		int mid = (low+high)/2;
		if(value>list[mid]){
			mid++;
			if(mid<high){
				midSearch(list,mid,high,value);
			}else{
				return mid;
			}
		}else if(value<list[mid]){
			mid--;
			if(mid>low){
				midSearch(list,low,mid,value);
			}else{
				return mid;
			}
		}
		return mid;
	}
	
	public int insertAndPairs(int[] list,int start, int end,int value, int sum){
		int j=0;
		for(j=end+1;j>start;j--){
			list[j]=list[j-1];//insert the least one into list head
			if(list[j]>2*value){//find pairs
				sum ++;
			}
		}
		list[start] = value;
		return sum;
	}
	
	public int getPairs(int[] list) throws InterruptedException{
		int low, mid, high;
		int i,j;
		int len = list.length;
		int sum = 0;
		for(i=1;i<len;i++){//merge sort
			int cur = list[i];
			low = 0;
			high = i-1;
			mid = (low+high)/2;
			if(cur <= list[0]){//[0,i-1][i,len-1],previous list is in order
				sum = insertAndPairs(list,0,i-1,cur,sum);
				list[0] = cur;
			}else if(cur>=list[i-1]){//no need action
				continue; 
			}else{ //mid search
				int index = midSearch(list,low,high,cur);
				//compare all values after index, [index,high]
				sum = insertAndPairs(list,index,i-1,cur,sum);
			}
		}
		return sum;
	}

	public static void main(String[] args) throws InterruptedException{
		int [] list = {2,4,3,5,1};
		ReversePairs rp = new ReversePairs();
		int sum = rp.getPairs(list);
		System.out.println("\n\nRES: "+sum);
	}
}

---------------------------------------------------------------------------------------------------

本文链接:http://blog.csdn.net/karen0310/article/details/xx

请尊重作者的劳动成果,转载请注明出处!

---------------------------------------------------------------------------------------------------


  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值