Count of Smaller Number before itself

Give you an integer array (index from 0 to n-1, where n is the size of this array, value from 0 to 10000) . For each element Ai in the array, count the number of element before this elementAi is smaller than it and return count number array.

Example

For array [1,2,7,8,5], return [0,1,2,3,2]

Analysis:

Create a segement tree in which start, end, and count refer to the total numbers from start to end. And at the beginning, we set the count to 0. However, every time when we query from the tree, say, we query 10, we first call query(root, 0, 9), and then update the count of 10 in the tree.

 1 public class Solution {
 2    /**
 3      * @param A: An integer array
 4      * @return: Count the number of element before this element 'ai' is 
 5      *          smaller than it and return count number array
 6      */
 7     SegmentTreeNode root;
 8      
 9     class SegmentTreeNode {
10         // here, start and end refer to the actual number
11         public int start, end;
12         public int count;
13         public SegmentTreeNode left, right;
14         public SegmentTreeNode(int start, int end, int count) {
15               this.start = start;
16               this.end = end;
17               this.count = count;
18               this.left = this.right = null;
19         }
20     }
21     // here, start and end refer to the actual number
22     public SegmentTreeNode build(int start, int end) {
23         if(start > end) return null;
24         
25         SegmentTreeNode root = new SegmentTreeNode(start, end, 0);
26         
27         if(start != end) {
28             int mid = (start + end) / 2;
29             root.left = build(start, mid);
30             root.right = build(mid + 1, end);
31         }
32         return root;
33     }
34     public int querySegmentTree(SegmentTreeNode root, int start, int end) {
35         if(start == root.start && root.end == end) { 
36             return root.count;
37         }
38         int mid = (root.start + root.end) / 2;
39         
40         if (start > mid) {
41             return querySegmentTree(root.right, start, end);
42         } else if (end <= mid) {
43             return querySegmentTree(root.left, start, end);
44         } else {
45             return querySegmentTree(root.left, start, mid) + querySegmentTree(root.right, mid + 1, end);
46         }
47     }
48     public void modifySegmentTree(SegmentTreeNode root, int index, int value) {
49         if(root.start == index && root.end == index) {
50             root.count += value;
51             return;
52         }
53         if (index < root.start || index > root.end) return;
54         
55         // 查询
56         int mid = (root.start + root.end) / 2;
57         if(index <= mid) {
58             modifySegmentTree(root.left, index, value);
59         } else {
60             modifySegmentTree(root.right, index, value);
61         }
62         //更新
63         root.count = root.left.count + root.right.count;
64     }
65     public ArrayList<Integer> countOfSmallerNumberII(int[] A) {
66         // write your code here
67         root = build(0, 10000);
68         ArrayList<Integer> ans = new ArrayList<Integer>();
69         for(int i = 0; i < A.length; i++) {
70             int res = 0;
71             if (A[i] > 0) { // if A[i] == 0, we don't need to query
72                 res = querySegmentTree(root, 0, A[i]-1);
73             }
74             modifySegmentTree(root, A[i], 1);
75             ans.add(res);
76         }
77         return ans;
78     }
79 }

 

posted @ 2016-07-14 21:16  北叶青藤  阅读(350)  评论(0编辑  收藏  举报