-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathHasSumDP.java
103 lines (87 loc) · 3.44 KB
/
HasSumDP.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
/*
Problem Statement:
------------------
Write a function `howSum(targetSum, numbers)` that takes in a targetSum and an array of numbers as arguments.
The function should return an array containing any combination of elements that add up to exactly the targetSum. If there is no combination that adds up to the targetSum, then return null.
If there are multiple combinations possible, you may return any single one.
Examples:
---------
hasSum(7, [2, 3]) --> [3, 2, 2]
hasSum(7, [2, 4]) --> [4, 3]
hasSum(8, [2, 3, 5]) --> null
hasSum(7, [5, 3, 4, 7]) --> [2, 2, 2, 2]
hasSum(300, [7, 14]) --> null
*/
import java.util.*;
public class HasSumDP {
public static Object hasSumDP(int targetSum, int numbers[], ArrayList<Integer> result, Map<Integer, ArrayList<Integer>> dp) {
// Base Cases:
if (dp.containsKey(targetSum)) {
return dp.get(targetSum);
}
if (targetSum == 0) {
// If the targetSum becomes 0, we have found a result. So, returning an empty
// array.
return (new ArrayList<Integer>());
}
if (targetSum < 0) {
// If the targetSum becomes -ve, the path certainly does not contain our answer.
return null;
}
for (int i = 0; i < numbers.length; i++) {
int remainingSum = targetSum - numbers[i];
// If the function has not returned null,
// the current element (i.e. numbers[i]), may lead to our answer.
if (hasSumDP(remainingSum, numbers, result, dp) != null) {
result.add(numbers[i]);
dp.put(targetSum, result);
return result;
}
}
// backtracking, returning null
dp.put(targetSum, null);
return null;
}
// We can also use a variable to maintain the least sized array.
public static void main(String[] args) {
int targetSum = 300;
int numbers[] = { 7, 14 };
Map<Integer, ArrayList<Integer>> dp = new HashMap<>();
// Using the result array for the thread safety purpose only..
ArrayList<Integer> result = new ArrayList<>();
System.out.println(hasSumDP(targetSum, numbers, result, dp));
}
}
/*
// Thread unsafe code without using ArrayList.
// -------------------------------------------
public static ArrayList hasSumDP(int targetSum, int numbers[], Map<Integer, ArrayList<Integer>> dp) {
// Base Cases:
if (dp.containsKey(targetSum)) {
return dp.get(targetSum);
}
if (targetSum == 0) {
// If the targetSum becomes 0, we have found a result. So, returning an empty
// array.
return (new ArrayList<Integer>());
}
if (targetSum < 0) {
// If the targetSum becomes -ve, the path certainly does not contain our answer.
return null;
}
for (int i = 0; i < numbers.length; i++) {
int remainingSum = targetSum - numbers[i];
// If the function has not returned null,
// the current element (i.e. numbers[i]), may lead to our answer.
ArrayList<Integer> answer = hasSumDP(remainingSum, numbers, dp);
if (answer != null) {
answer.add(numbers[i]);
dp.put(targetSum, answer);
return answer;
}
}
// backtracking, returning null
dp.put(targetSum, null);
return null;
}
*/