Given an array and a value, find all the triplets in the array whose sum is equal to the given value. For example, if the given array is
{12, 3, 4, 1, 6, 9}and the given sum is24, then this is one triplet(12, 3 and 9)which contributes to the total sum of 24.
Solution for given example:
6, 9, 9
6, 6, 12
3, 9, 12
Conditions:
The ordering of the numbers in the solution does not matter.
Duplicate triplet is not allowed.
A number is not allowed to be used multiple times.
This question was asked here.
Here is my code which addresses all the issues. One concern is the code looks a little muddy which I want to avoid in the production grade code. Any constructive feedback is appreciated.
public class ThreeSum {
static class Triplet {
final List<Integer> triplets;
public Triplet(int x, int y, int z) {
triplets = Arrays.asList(x, y, z);
Collections.sort(triplets);
}
@Override
public int hashCode() {
return Objects.hash(triplets.get(0), triplets.get(1), triplets.get(2));
}
@Override
public boolean equals(Object o) {
if (o instanceof Triplet) {
Triplet other = (Triplet) o;
return other.triplets.get(0) == this.triplets.get(0) &&
other.triplets.get(1) == this.triplets.get(1) &&
other.triplets.get(2) == this.triplets.get(2);
}
return false;
}
@Override
public String toString() {
return String.format("(%d, %d, %d)", triplets.get(0), triplets.get(1), triplets.get(2));
}
}
public static Set<Triplet> findTriplets(int numbers[], int targetSum) {
Set<Triplet> triplets = new HashSet<>();
// insert all pairs in the look up table
Map<Integer, int[]> lookup = new HashMap<>();
for (int i = 0; i < numbers.length - 1; i++) {
for (int j = i + 1; j < numbers.length; j++) {
int total = numbers[i] + numbers[j];
lookup.put(total, new int[]{i, j});
}
}
// look for the complement, if found viola! here you go with the triplet
for (int currentIndex = 0; currentIndex < numbers.length; currentIndex++) {
int complement = targetSum - numbers[currentIndex];
if (lookup.containsKey(complement)) {
int indexes[] = lookup.get(complement);
if (currentIndex != indexes[0] && currentIndex != indexes[1]) {
int x = numbers[indexes[0]], y = numbers[indexes[1]];
triplets.add(new Triplet(x, y, numbers[currentIndex]));
}
}
}
return triplets;
}
}