(248) Count of Smaller Number
Give you an integer array (index from 0 to n-1, where n is the size of this array, value from 0 to 10000) and an query list. For each query, give you an integer, return the number of element in the array that are smaller that the given integer.
http://ying.ninja/?p=775
Solution: Version 1. sort + binary search O(nlogn) Time
//Version 2. Segment Tree. not as efficient as version 1.
//check <Count of Smaller Number II>
Solution 2: Segment tree
http://www.tangjikai.com/algorithms/lintcode-248-count-of-smaller-number
O(n+mlogn) time (m queries, n segment tree nodes)
O(logn) space
Solution 1: binary search
https://xmruibi.gitbooks.io/interview-preparation-notes/content/Algorithm/BinarySearch/CountSmallerNumber.html
1. Solution by Loop with O(n^2)
Give you an integer array (index from 0 to n-1, where n is the size of this array, value from 0 to 10000) and an query list. For each query, give you an integer, return the number of element in the array that are smaller that the given integer.
Example
For array
[1,2,7,8,5], and queries [1,8,5], return [0,4,2]Solution: Version 1. sort + binary search O(nlogn) Time
//Version 2. Segment Tree. not as efficient as version 1.
//check <Count of Smaller Number II>
public ArrayList<Integer> countOfSmallerNumber(int[] A, int[] queries) { //Version 1. sort + binary search //Version 2. Segment Tree. not as efficient as version 1. //check <Count of Smaller Number before itself> ArrayList<Integer> result = new ArrayList<>(); if (A == null || queries == null) { return result; } if (A.length == 0) { for (int i = 0; i < queries.length; i++) { result.add(0); } return result; } Arrays.sort(A); for (int i = 0; i < queries.length; i++) { int target = queries[i]; //find the last element A[i]<target, i+1 is the number int start = 0; int end = A.length - 1; while (start + 1 < end) { int mid = start + (end - start) / 2; if (A[mid] < target) { start = mid; } else { end = mid; } } if (A[end] < target) { result.add(end + 1); } else if (A[start] < target) { result.add(start + 1); } else { result.add(0); } } return result;}http://www.tangjikai.com/algorithms/lintcode-248-count-of-smaller-number
O(n+mlogn) time (m queries, n segment tree nodes)
O(logn) space
class SegmentTreeNode:
def __init__(self, start, end, count):
self.start, self.end, self.count = start, end, count
self.left, self.right = None, None
"""
@param A: A list of integer
@return: The number of element in the array that
are smaller that the given integer
"""
def countOfSmallerNumber(self, A, queries):
# write your code here
# build segmeng tree
root = self.build(0, 10000)
ans = []
# modify count value for each
for i in A:
self.modify(root, i, 1)
for i in queries:
res = 0
if i > 0:
res = self.query(root, 0, i - 1)
ans.append(res)
return ans
def build(self, start, end):
if start >= end:
return SegmentTreeNode(start, end, 0)
mid = start + (end - start) / 2
l = self.build(start, mid)
r = self.build(mid+1, end)
root = SegmentTreeNode(start, end, 0)
root.left = l
root.right = r
return root
def modify(self, root, index, value):
if root.start == index and root.end == index:
root.count += value
return
# query
mid = root.start + (root.end - root.start) / 2
if root.start <= index <= mid:
self.modify(root.left, index, value)
if mid < index <= root.end:
self.modify(root.right, index, value)
root.count = root.left.count + root.right.count
def query(self, root, start, end):
if start == root.start and end == root.end:
return root.count
mid = root.start + (root.end - root.start) / 2
lCount = rCount = 0
if start <= mid:
if end > mid:
lCount = self.query(root.left, start, mid)
else:
lCount = self.query(root.left, start, end)
if end > mid:
if start <= mid:
rCount = self.query(root.right, mid+1, end)
else:
rCount = self.query(root.right, start, end)
return lCount + rCount
https://codesolutiony.wordpress.com/2015/05/21/lintcode-count-of-smaller-number/ public ArrayList<Integer> countOfSmallerNumber(int[] A, int[] queries) { ArrayList<Integer> res = new ArrayList<Integer>(); if (A == null || queries == null || queries.length == 0) { return res; } Arrays.sort(A); MaxNode root = buildTree(A, 0, A.length - 1); for (int q : queries) { res.add(query(A, root, q)); } return res; } private MaxNode buildTree(int[] A, int start, int end) { if (start > end) { return null; } MaxNode root = new MaxNode(start, end); if (start == end) { root.val = A[start]; } else { root.left = buildTree(A, start, (start+end)/2); root.right = buildTree(A, (start+end)/2+1, end); root.val = root.left == null ? root.right.val : Math.max(root.left.val, root.right == null ? 0 : root.right.val); } return root; } private int query(int[] A, MaxNode root, int val) { if (root == null || A[root.start] > val) { return 0; } if (root.val < val) { return root.end - root.start + 1; } return query(A, root.left, val) + query(A, root.right, val); } class MaxNode { int start; int end; int val; //how many nodes are between the range start - end (inclusive) MaxNode left; MaxNode right; public MaxNode() { } public MaxNode(int start, int end) { this.start = start; this.end = end; } public MaxNode(int start, int end, int val) { this(start, end); this.val = val; } } public ArrayList<Integer> countOfSmallerNumber(int[] A, int[] queries) { Arrays.sort(A); ArrayList<Integer> res = new ArrayList<Integer>(); for (int q : queries) { res.add(binarySearch(A, q)); } return res; } private int binarySearch(int[] A, int val) { int start = 0, end = A.length - 1; int res = 0; while (start <= end) { int mid = (start + end) / 2; if (A[mid] >= val) { end = mid - 1; } else { res = mid + 1; start = mid + 1; } } return res; }1. Solution by Loop with O(n^2)
public ArrayList<Integer> countOfSmallerNumber(int[] A, int[] queries) {
ArrayList<Integer> res = new ArrayList<>();
if(A == null || queries == null)
return res;
for(int i = 0; i < queries.length; i++) {
int cnt = 0;
for(int j = 0; j < A.length; j++) {
if(A[j] < queries[i])
cnt++;
}
res.add(cnt);
}
return res;
}
Read full article from (248) Count of Smaller Number