https://www.geeksforgeeks.org/find-smallest-range-containing-elements-from-k-lists/
Given 3 sorted arrays. Find(x,y,z), (where x is from 1st array, y is from 2nd array, and z is from 3rd array), such that Max(x,y,z) - Min(x,y,z) is minimum.
public static int findMinDistanceSortedArrays(
List<? extends List<Integer>> arrs) {
// Pointers for each of arrs.
List<Integer> idx = new ArrayList<>(arrs.size());
for (List<Integer> arr : arrs) {
idx.add(0);
}
int minDis = Integer.MAX_VALUE;
// contains arrs.size() elements
NavigableSet<ArrData> currentHeads = new TreeSet<>();
// Each of arrs puts its minimum element into current_heads.
for (int i = 0; i < arrs.size(); ++i) {
if (idx.get(i) >= arrs.get(i).size()) {
return minDis;
}
currentHeads.add(new ArrData(i, arrs.get(i).get(idx.get(i))));
}
while (true) {
minDis = Math.min(minDis, currentHeads.last().val
- currentHeads.first().val);
int tar = currentHeads.first().idx;
// Return if there is no remaining element in one array.
idx.set(tar, idx.get(tar) + 1);
if (idx.get(tar) >= arrs.get(tar).size()) {
return minDis;
}
currentHeads.pollFirst();
currentHeads.add(new ArrData(tar, arrs.get(tar).get(idx.get(tar))));
}
}
public static class ArrData implements Comparable<ArrData> {
public int idx;
public int val;
public ArrData(int idx, int val) {
this.idx = idx;
this.val = val;
}
public int compareTo(ArrData o) {
int result = Integer.valueOf(val).compareTo(o.val);
if (result == 0) {
result = Integer.valueOf(idx).compareTo(o.idx);
}
return result;
}
}
Given k sorted lists of integers of size n each, find the smallest range that includes at least element from each of the k lists. If more than one smallest ranges are found, print any one of them.
Example :
Input: K = 3 arr1[] : [4, 7, 9, 12, 15] arr2[] : [0, 8, 10, 14, 20] arr3[] : [6, 12, 16, 30, 50] Output: The smallest range is [6 8] Explanation: Smallest range is formed by number 7 from first list, 8 from second list and 6 from third list.
A Better efficient approach is to use min heap. Below are the steps –
- Create a min heap of size k and insert first elements of all k lists into the heap.
- Maintain two variables min and max to store minimum and maximum values present in the heap at any point. Note min will always contain value of the root of the heap.
- Repeat following steps
- Get minimum element from heap (minimum is always at root) and compute the range.
- Replace heap root with next element of the list from which the min element is extracted. After replacing the root, heapify the tree. Update max if next element is greater. If the list doesn’t have any more elements, break the loop
Compute the closest entries in three sorted arrays
http://www.careercup.com/question?id=14805690Given 3 sorted arrays. Find(x,y,z), (where x is from 1st array, y is from 2nd array, and z is from 3rd array), such that Max(x,y,z) - Min(x,y,z) is minimum.
public int minGap(int[] a, int[] b, int[] c)
{
int diff = Integer.MAX_VALUE;
int min = Integer.MAX_VALUE;
int max = Integer.MIN_VALUE;
int i, j, k;
for(i = 0, j = 0, k = 0; i < a.length && j < b.length && k < c.length;) {
min = Math.min(a[i], Math.min(b[j], c[k]));
max = Math.max(a[i], Math.max(b[j], c[k]));
diff = Math.min(diff, max - min);
if(diff == 0) break;
if(a[i] == min) i++;
else if(b[j] == min) j++;
else k++;
}
return diff;
}
MinimumDistance3SortedArrays.javapublic static int findMinDistanceSortedArrays(
List<? extends List<Integer>> arrs) {
// Pointers for each of arrs.
List<Integer> idx = new ArrayList<>(arrs.size());
for (List<Integer> arr : arrs) {
idx.add(0);
}
int minDis = Integer.MAX_VALUE;
// contains arrs.size() elements
NavigableSet<ArrData> currentHeads = new TreeSet<>();
// Each of arrs puts its minimum element into current_heads.
for (int i = 0; i < arrs.size(); ++i) {
if (idx.get(i) >= arrs.get(i).size()) {
return minDis;
}
currentHeads.add(new ArrData(i, arrs.get(i).get(idx.get(i))));
}
while (true) {
minDis = Math.min(minDis, currentHeads.last().val
- currentHeads.first().val);
int tar = currentHeads.first().idx;
// Return if there is no remaining element in one array.
idx.set(tar, idx.get(tar) + 1);
if (idx.get(tar) >= arrs.get(tar).size()) {
return minDis;
}
currentHeads.pollFirst();
currentHeads.add(new ArrData(tar, arrs.get(tar).get(idx.get(tar))));
}
}
public static class ArrData implements Comparable<ArrData> {
public int idx;
public int val;
public ArrData(int idx, int val) {
this.idx = idx;
this.val = val;
}
public int compareTo(ArrData o) {
int result = Integer.valueOf(val).compareTo(o.val);
if (result == 0) {
result = Integer.valueOf(idx).compareTo(o.idx);
}
return result;
}
}