Question: Given an unsorted array of positive integers, is it possible to find a pair of integers from that array that sum up to a given sum?
Constraints: This shou
def pair_sum(arr,k):
counter = 0
lookup = set()
for num in arr:
if k-num in lookup:
counter+=1
else:
lookup.add(num)
return counter
pass
pair_sum([1,3,2,2],4)
The solution in python
Ruby implementation
ar1 = [ 32, 44, 68, 54, 65, 43, 68, 46, 68, 56]
for i in 0..ar1.length-1
t = 100 - ar1[i]
if ar1.include?(t)
s= ar1.count(t)
if s < 2
print s , " - " , t, " , " , ar1[i] , " pair ", i, "\n"
end
end
end
This might be possible if the array contains numbers, the upper limit of which is known to you beforehand. Then use counting sort or radix sort(o(n)) and use the algorithm which @PengOne suggested.
Otherwise I can't think of O(n) solution.But O(nlgn) solution works in this way:-
First sort the array using merge sort or quick sort(for inplace). Find if sum - array_element is there in this sorted array. One can use binary search for that.
So total time complexity: O(nlgn) + O(lgn) -> O(nlgn).
take two pointers one starts from 0th index of array, and another from end of array say (n-1).
run the loop until low <= high
Sum = arr[low] + arr[high]
if(sum == target)
print low, high
if(sum < target)
low++
if(sum > target)
high--
Step 2 to 10 takes O(n) time, and counting sort takes O(n). So total time complexity will be O(n).
Here is a solution in python:
a = [9, 8, 9, 2, 15, 11, 21, 8, 9, 2, 2, 8, 9, 2, 15, 11, 21, 8, 9, 2, 9, 8, 9, 2, 15, 11, 21, 8, 9, 2, 2, 8, 9, 2, 15, 11, 2, 8, 9, 2, 2, 8,
9, 2, 15, 11, 21, 8, 9, 12, 2, 8, 9, 2, 15, 11, 21, 7, 9, 2, 23, 8, 9, 2, 15, 11, 21, 8, 9, 2, 2, 12, 9, 2, 15, 11, 21, 8, 9, 2, 2,
8, 9, 2, 15, 11, 21, 8, 9, 2, 2, 8, 9, 2, 15, 11, 21, 8, 9, 2, 2, 8, 9, 2, 15, 11, 21, 8, 9, 2, 2, 7.12, 9, 2, 15, 11, 21, 8, 9, 2, 2, 8, 9,
2, 15, 11, 21, 8, 9, 2, 2, 8, 9, 2, 15, 11, 21, 8, 9, 2, 2, 8, 9, 2, 15, 11, 21, 8, 9, 2, 2, 8, 9, 2, 15, 11, 21, 8, 0.87, 78]
i = 0
j = len(a) - 1
my_sum = 8
finded_numbers = ()
iterations = 0
while(OK):
iterations += 1
if (i < j):
i += 1
if (i == j):
if (i == 0):
OK = False
break
i = 0
j -= 1
if (a[i] + a[j] == my_sum):
finded_numbers = (a[i], a[j])
OK = False
print finded_numbers
print iterations
If you have a sorted array you can find such a pair in O(n) by moving two pointers toward the middle
i = 0
j = n-1
while(i < j){
if (a[i] + a[j] == target) return (i, j);
else if (a[i] + a[j] < target) i += 1;
else if (a[i] + a[j] > target) j -= 1;
}
return NOT_FOUND;
The sorting can be made O(N) if you have a bound on the size of the numbers (or if the the array is already sorted in the first place). Even then, a log n factor is really small and I don't want to bother to shave it off.
proof:
If there is a solution (i*, j*)
, suppose, without loss of generality, that i
reaches i*
before j
reaches j*
. Since for all j'
between j*
and j
we know that a[j'] > a[j*]
we can extrapolate that a[i] + a[j'] > a[i*] + a[j*] = target
and, therefore, that all the following steps of the algorithm will cause j to decrease until it reaches j*
(or an equal value) without giving i
a chance to advance forward and "miss" the solution.
The interpretation in the other direction is similar.