LeetCode 493. Reverse Pairs

原题链接在这里:https://leetcode.com/problems/reverse-pairs/

题目:

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:

  1. The length of the given array will not exceed 50,000.
  2. All the numbers in the input array are in the range of 32-bit integer.

题解:

It is obvious that it takes O(n^2) to solve it by brute force. The question is how to optimize it.

For question like it, try to cut it into small subproblems and use divide and conquer.

Usually it could be cut by 2 ways: T(i, j) = T(i, j-1) + nums[j]. Or T(i, j) = T(i, mid) + T(mid+1, j).

To optimize it, use the 2nd way here.

The reverse pairs could happen in 3 parts, T(i, mid), T(mid+1, j) and T(i, j).

Let divide function return the count of subproblem, and also sort the subarray.

Then when we get the count of subproblem, nums[l ~ mid] is alrady sorted, so is nums[mid+1, r].

Use two pointers i and j. Move j while nums[i]/2.0 > nums[j]. Here to avoid overflow, use /2.0 but not *2 on the other side. Also must use 2.0, but not 2. e.g. 3/2.0 > 1, but 3/2==1.

j - (mid+1) pairs found. Then move i. now nums[i] is bigger, j only needs to move forwad, there is no need to reset it to mid+1.

Accumlate the res and finally sort nums[i ~ j].

Time Complexity: O(n(logn)^2). T(n) = 2*T(n/2) + O(nlogn). Mater theorem, T(n) = O(n(logn)^2). Each level, it takes O(nlogn) for sorting. There are logn levels.

Space: O(logn). stack space.

AC Java:

 1 class Solution {
 2     public int reversePairs(int[] nums) {
 3         if(nums == null || nums.length < 2){
 4             return 0;
 5         }
 6
 7         return mergeSort(nums, 0, nums.length-1);
 8     }
 9
10     private int mergeSort(int [] nums, int l, int r){
11         if(l >= r){
12             return 0;
13         }
14
15         int mid = l + (r-l)/2;
16         int count = mergeSort(nums, l, mid) + mergeSort(nums, mid+1, r);
17         int i = l;
18         int j = mid+1;
19         while(i<=mid){
20             while(j<=r && nums[i]/2.0 > nums[j]){
21                 j++;
22             }
23
24             count += j-(mid+1);
25             i++;
26         }
27
28         Arrays.sort(nums, l, r+1);
29         return count;
30     }
31 }

Since left and right parts are alrady sorted. Could use O(n) time to sort. This reduces time complexity to O(n) on each level.

Time Complexity: O(nlogn).

Space: O(logn).

AC Java:

 1 class Solution {
 2     int [] copy;
 3     public int reversePairs(int[] nums) {
 4         if(nums == null || nums.length < 2){
 5             return 0;
 6         }
 7
 8         copy = new int[nums.length];
 9         return mergeSort(nums, 0, nums.length-1);
10     }
11
12     private int mergeSort(int [] nums, int l, int r){
13         if(l >= r){
14             return 0;
15         }
16
17         int mid = l + (r-l)/2;
18         int count = mergeSort(nums, l, mid) + mergeSort(nums, mid+1, r);
19         int i = l;
20         int j = mid+1;
21         while(i<=mid){
22             while(j<=r && nums[i]/2.0 > nums[j]){
23                 j++;
24             }
25
26             count += j-(mid+1);
27             i++;
28         }
29
30         merge(nums, l, mid, r);
31         return count;
32     }
33
34     private void merge(int [] nums, int l, int mid, int r){
35         for(int cur = l; cur<=r; cur++){
36             copy[cur] = nums[cur];
37         }
38
39         int i = l;
40         int j = mid+1;
41         int po = i;
42         while(i<=mid || j<=r){
43             if(i>mid || (j<=r && copy[i]>copy[j])){
44                 nums[po++] = copy[j++];
45             }else{
46                 nums[po++] = copy[i++];
47             }
48         }
49     }
50 }

类似Count of Smaller Numbers After Self.

原文地址:https://www.cnblogs.com/Dylan-Java-NYC/p/11623953.html

时间: 2024-08-14 22:44:46

LeetCode 493. Reverse Pairs的相关文章

493. Reverse Pairs

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:

493. Reverse Pairs(BST, BIT, MergeSort)

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:

【leetcode】493. Reverse Pairs

好吧这其实是一次小比赛,在回上海前的周末.好久没打比赛,简单题也只是AK了而已,还TM错了一次.最后45名57分钟加一次罚时,第一名18分钟,好吧.也行了对于业余组选手. 错在没考虑到乘2会超max_int. 程序没了,也没心情找了.孤单的情人节. 貌似有两个人被发现作弊了我变成了43名,还找到了程序,也算一点小小的安慰吧. class Solution { public: int reversePairs(vector<int>& aa) { vector<long long&

493 Reverse Pairs 翻转对

给定一个数组 nums ,如果 i < j 且 nums[i] > 2*nums[j] 我们就将 (i, j) 称作一个重要翻转对.你需要返回给定数组中的重要翻转对的数量.示例 1:输入: [1,3,2,3,1]输出: 2示例 2:输入: [2,4,3,5,1]输出: 3注意:    给定数组的长度不会超过50000.    输入数组中的所有数字都在32位整数的表示范围内.详见:https://leetcode.com/problems/reverse-pairs/description/ C

LeetCode -Reverse Pairs

my solution: class Solution { public: int reversePairs(vector<int>& nums) { int length=nums.size(); int count=0; for (int i=0;i<length;i++) { for(int j=i+1;j<length;j++) { if(nums[i]>2*nums[j]) count++; } } return count; } }; wrong answ

[LeetCode] Reverse Pairs 翻转对

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:

Reverse Pairs

For an array A, if i < j, and A [i] > A [j], called (A [i], A [j]) is a reverse pair.return total of reverse pairs in A. Example Given A = [2, 4, 1, 3, 5] , (2, 1), (4, 1), (4, 3) are reverse pairs. return 3 Solution 1: the same as the leetcode ques

LeetCode:Reverse Integer - 翻转数字

1.题目名称 Reverse Integer(翻转数字) 2.题目地址 https://leetcode.com/problems/reverse-integer/ 3.题目内容 英文:Reverse digits of an integer. 中文:翻转一个正整数的各位,形成一个新数字 例如:x = 123, return 321:x = -123, return -321 4.一个有瑕疵的方法(不能AC) 一个比较好想到的方法,是先将输入的数字转换为字符串,再将字符串翻转后转换为数字.这个方

【leetcode】Reverse Words in a String

问题:给定一个字符串,字符串中包含若干单词,每个单词间由空格分隔,将单词逆置,即第一个单词成为最后一个单词,一次类推. 说明:字符串本身可能包含前导空格或后导空格,单词间可能包含多个空格,要求结果中去掉前导和后导空格,单词间空格只保留一个. 与rotate函数类似,先逆置每个单词,再将所有字符串逆置. void reverseWords(string &s) { if(s.size() == 0) return; char blank = ' '; size_t len = s.size();