[algorithm] find all subsets that sum to a particular value

Given a set of numbers: {1, 3, 2, 5, 4, 9}, find the number of subsets that sum to a particular value (say, 9 for this example).

This is similar to subset sum problem with the slight difference that instead of checking if the set has a subset that sums to 9, we have to find the number of such subsets. I am following the solution for subset sum problem here. But and I am wondering how I can modify it to return the count of subsets.

This question is related to algorithm recursion subset

The answer is


The usual DP solution is true for the problem.

One optimization you may do, is to keep a count of how many solutions exist for the particular sum rather than the actual sets that make up that sum...


This my dynamical programming implementation in JS. It will return an array of arrays, each holding the subsequences summing to the provided target value.

_x000D_
_x000D_
function getSummingItems(a,t){_x000D_
  return a.reduce((h,n) => Object.keys(h)_x000D_
                                 .reduceRight((m,k) => +k+n <= t ? (m[+k+n] = m[+k+n] ? m[+k+n].concat(m[k].map(sa => sa.concat(n)))_x000D_
                                                                                      : m[k].map(sa => sa.concat(n)),m)_x000D_
                                                                 :  m, h), {0:[[]]})[t];_x000D_
}_x000D_
var arr = Array(20).fill().map((_,i) => i+1), // [1,2,..,20]_x000D_
    tgt = 42,_x000D_
    res = [];_x000D_
_x000D_
console.time("test");_x000D_
res = getSummingItems(arr,tgt);_x000D_
console.timeEnd("test");_x000D_
console.log("found",res.length,"subsequences summing to",tgt);_x000D_
console.log(JSON.stringify(res));
_x000D_
_x000D_
_x000D_


public class SumOfSubSet {

    public static void main(String[] args) {
        // TODO Auto-generated method stub

        int a[] = {1,2};
        int sum=0;
        if(a.length<=0) {
            System.out.println(sum);
        }else {
        for(int i=0;i<a.length;i++) {
            sum=sum+a[i];
            for(int j=i+1;j<a.length;j++) {
                sum=sum+a[i]+a[j];
            }
        }
        System.out.println(sum);

        }


    }

}

This my program in ruby . It will return arrays, each holding the subsequences summing to the provided target value.

array = [1, 3, 4, 2, 7, 8, 9]

0..array.size.times.each do |i| 
  array.combination(i).to_a.each { |a| print a if a.inject(:+) == 9} 
end

You may use Dynamic Programmining. Algo complexity is O(Sum * N) and use O(Sum) memory.

Here's my implementation in C#:

private static int GetmNumberOfSubsets(int[] numbers, int sum)
{
    int[] dp = new int[sum + 1];
    dp[0] = 1;
    int currentSum =0;
    for (int i = 0; i < numbers.Length; i++)
    {
        currentSum += numbers[i];
        for (int j = Math.Min(sum, currentSum); j >= numbers[i]; j--)
            dp[j] += dp[j - numbers[i]];
    }

    return dp[sum];
}

Notes: As number of subsets may have value 2^N it easy may overflows int type.

Algo works only for positive numbers.


Here is a Java Solution:

This is a classical Back tracking problem for finding all possible subsets of the integer array or set that is the input and then filtering those which sum to e given target

import java.util.HashSet;
import java.util.StringTokenizer;

/**
 * Created by anirudh on 12/5/15.
 */
public class findSubsetsThatSumToATarget {

    /**
     * The collection for storing the unique sets that sum to a target.
     */
    private static HashSet<String> allSubsets = new HashSet<>();

    /**
     * The String token
     */
    private static final String token = " ";

    /**
     * The method for finding the subsets that sum to a target.
     *
     * @param input  The input array to be processed for subset with particular sum
     * @param target The target sum we are looking for
     * @param ramp   The Temporary String to be beefed up during recursive iterations(By default value an empty String)
     * @param index  The index used to traverse the array during recursive calls
     */
    public static void findTargetSumSubsets(int[] input, int target, String ramp, int index) {

        if(index > (input.length - 1)) {
            if(getSum(ramp) == target) {
                allSubsets.add(ramp);
            }
            return;
        }

        //First recursive call going ahead selecting the int at the currenct index value
        findTargetSumSubsets(input, target, ramp + input[index] + token, index + 1);
        //Second recursive call going ahead WITHOUT selecting the int at the currenct index value
        findTargetSumSubsets(input, target, ramp, index + 1);
    }

    /**
     * A helper Method for calculating the sum from a string of integers
     *
     * @param intString the string subset
     * @return the sum of the string subset
     */
    private static int getSum(String intString) {
        int sum = 0;
        StringTokenizer sTokens = new StringTokenizer(intString, token);
        while (sTokens.hasMoreElements()) {
            sum += Integer.parseInt((String) sTokens.nextElement());
        }
        return sum;
    }

    /**
     * Cracking it down here : )
     *
     * @param args command line arguments.
     */
    public static void main(String[] args) {
        int [] n =  {24, 1, 15, 3, 4, 15, 3};
        int counter = 1;
        FindSubsetsThatSumToATarget.findTargetSumSubsets(n, 25, "", 0);
        for (String str: allSubsets) {
            System.out.println(counter + ") " + str);
            counter++;
        }
    }
}

It gives space separated values of the subsets that sum to a target.

Would print out commma separated values for the subsets that sum to 25 in {24, 1, 15, 3, 4, 15, 3}

1) 24 1

2) 3 4 15 3

3) 15 3 4 3


The same site geeksforgeeks also discusses the solution to output all subsets that sum to a particular value: http://www.geeksforgeeks.org/backttracking-set-4-subset-sum/

In your case, instead of the output sets, you just need to count them. Be sure to check the optimized version in the same page, as it is an NP-complete problem.

This question also has been asked and answered before in stackoverflow without mentioning that it's a subset-sum problem: Finding all possible combinations of numbers to reach a given sum


Python function subset that return subset of list that adds up to a particular value

def subset(ln, tar):#ln=Lenght Of String, tar= Target
s=[ int(input('Insert Numeric Value Into List:')) for i in range(ln) ]#Inserting int Values in s of type<list>
if sum(s) < tar:#Sum of List is less than Target Value
    return
elif sum(s) == tar:#Sum of list is equal to Target Value i.e for all values combinations
    return s
elif tar in s:#Target value present in List i.e for single value
    return s[s.index(tar)]
else:#For remaining possibilities i.e for all except( single and all values combinations )
    from itertools import combinations# To check all combinations ==> itertools.combinations(list,r) OR return list of all subsets of length r
    r=[i+1 for i in range(1,ln-1)]# Taking r as only remaining value combinations, i.e. 
                                 # Except(  r=1 => for single value combinations AND r=length(list) || r=ln => For all value combinations
    lst=list()#For Storing all remaining combinations
    for i in range(len(r)):
        lst.extend(list( combinations(s,r[i]) ))
    for i in range(len(lst)):# To check remaining possibilities
        if tar == sum(lst[i]):
            return list(lst[i])

subset( int(input('Length of list:')), int(input('Target:')))


RUBY

This code will reject the empty arrays and returns the proper array with values.

def find_sequence(val, num)
  b = val.length
  (0..b - 1).map {|n| val.uniq.combination(n).each.find_all {|value| value.reduce(:+) == num}}.reject(&:empty?)
end

val = [-10, 1, -1, 2, 0]
num = 2

Output will be [[2],[2,0],[-1,1,2],[-1,1,2,0]]


My backtracking solution :- Sort the array , then apply the backtracking.

void _find(int arr[],int end,vector<int> &v,int start,int target){
        if(target==0){
        for(int i = 0;i<v.size();i++){
            cout<<v[i]<<" ";
        }
        cout<<endl;
    }

    else{
        for(int i =  start;i<=end && target >= arr[i];i++){
            v.push_back(arr[i]);
            _find(arr,end,v,i+1,target-arr[i]);
            v.pop_back();
        }
    }
}

I have found that so many interviews are asking for this so I implemented a really quite simple and understandable solution. First I generate all the possible combinations, and from there, you can do whatever you want. Check this out:

public static void main(String[] args) {
        int[] numbers = new int[]{1, 2, 3, 4, 5};
        List<int[]> allPossibleCombinatiosForNumbers = new ArrayList<>();
        for (int i = 2; i < numbers.length; i++) {
            allPossibleCombinatiosForNumbers.addAll(getCombinationsOfNElements(numbers, i));
        }
        for (int[] combination : allPossibleCombinatiosForNumbers) {
            printArray(combination);
            printArrayIfNumbersSumExpectedValue(combination, 6);
        }
    }


    private static List<int[]> getCombinationsOfNElements(int[] numbers, int n) {
        int elementsKnown = n - 1;
        List<int[]> allCombinationsOfNElements = new ArrayList<>();
        for (int i = 0; i < numbers.length - elementsKnown; i++) {
            int[] combination = new int[n];
            for (int j = 0; j < n; j++) {
                combination[j] = numbers[i + j];
            }
            allCombinationsOfNElements.addAll(generationCombinations(combination, i + elementsKnown, numbers));
        }
        return allCombinationsOfNElements;
    }

    private static List<int[]> generationCombinations(int[] knownElements, int index, int[] numbers) {
        List<int[]> combinations = new ArrayList<>();
        for (int i = index; i < numbers.length; i++) {
            int[] combinationComplete = Arrays.copyOf(knownElements, knownElements.length);
            combinationComplete[knownElements.length - 1] = numbers[i];
            combinations.add(combinationComplete);
        }
        return combinations;
    }

    private static void printArray(int[] numbers) {
        System.out.println();
        for (int i = 0; i < numbers.length; i++) {
            System.out.print(numbers[i] + " ");
        }
    }

    private static void printArrayIfNumbersSumExpectedValue(int[] numbers, int expectedValue) {
        int total = 0;
        for (int i = 0; i < numbers.length; i++) {
            total += numbers[i];
        }
        if (total == expectedValue) {
            System.out.print("\n ----- Here is a combination you are looking for -----");
            printArray(numbers);
            System.out.print("\n -------------------------------");
        }
    }

Subset sum problem can be solved in O(sum*n) using dynamic programming. Optimal substructure for subset sum is as follows:

SubsetSum(A, n, sum) = SubsetSum(A, n-1, sum) || SubsetSum(A, n-1, sum-set[n-1])

SubsetSum(A, n, sum) = 0, if sum > 0 and n == 0 SubsetSum(A, n, sum) = 1, if sum == 0

Here A is array of elements, n is the number of elements of array A and sum is the sum of elements in the subset.

Using this dp, you can solve for the number of subsets for the sum.

For getting subset elements, we can use following algorithm:

After filling dp[n][sum] by calling SubsetSum(A, n, sum), we recursively traverse it from dp[n][sum]. For cell being traversed, we store path before reaching it and consider two possibilities for the element.

1) Element is included in current path.

2) Element is not included in current path.

Whenever sum becomes 0, we stop the recursive calls and print current path.

void findAllSubsets(int dp[], int A[], int i, int sum, vector<int>& p) { 

   if (sum == 0) { 
        print(p); 
        return; 
   } 

   // If sum can be formed without including current element
   if (dp[i-1][sum]) 
   { 
        // Create a new vector to store new subset 
        vector<int> b = p; 
        findAllSubsets(dp, A, i-1, sum, b); 
   } 

   // If given sum can be formed after including 
   // current element. 
   if (sum >= A[i] && dp[i-1][sum-A[i]]) 
   { 
        p.push_back(A[i]); 
        findAllSubsets(dp, A, i-1, sum-A[i], p); 
   } 

} 

Here is an efficient solution when there is a large set of inputs (i.e. 25 to 30)

I made efficiency gains in two ways:

  • Utilized a simple rolling wheel concept for binary counting through all possible iterations, rather than using mathematically expensive base conversion language features. This "wheel" is akin to an old mechanical counter or odometer. It recursively rolls forward as many positions as necessary until we surpass the number of binary digits we have (e.g., the count of numbers in our set).
  • The main gain is from not summing the entire candidate set each time. Instead, it maintains a running sum and each time it "rolls the wheel", it adjusts the running sum only for the pieces that changed from the last candidate set it tested. This saves a lot of computation since most "wheel rolls" only change a number or two.

This solution works with negative numbers, decimal amounts, and repeated input values. Due to the wonky way that floating point decimal math works in most languages, you will want to keep your input set to only a few decimal places or you may have some unpredictable behavior.

On my old 2012-era desktop computer the given code processes 25 input values in about 0.8 seconds in javascript/node.js, and 3.4 seconds in C#.

javascript

let numbers = [-0.47, -0.35, -0.19, 0.23, 0.36, 0.47, 0.51, 0.59, 0.63, 0.79, 0.85, 
0.91, 0.99, 1.02, 1.17, 1.25, 1.39, 1.44, 1.59, 1.60, 1.79, 1.88, 1.99, 2.14, 2.31];

let target = 24.16;

displaySubsetsThatSumTo(target, numbers);

function displaySubsetsThatSumTo(target, numbers)
{
    let wheel = [0];
    let resultsCount = 0;
    let sum = 0;
    
    const start = new Date();
    do {
        sum = incrementWheel(0, sum, numbers, wheel);
        //Use subtraction comparison due to javascript float imprecision
        if (sum != null && Math.abs(target - sum) < 0.000001) {
            //Found a subset. Display the result.
            console.log(numbers.filter(function(num, index) {
                return wheel[index] === 1;
            }).join(' + ') + ' = ' + target);
            resultsCount++;
        }
    } while (sum != null);
    const end = new Date();
    
    console.log('--------------------------');
    console.log(`Processed ${numbers.length} numbers in ${(end - start) / 1000} seconds (${resultsCount} results)`);
}

function incrementWheel(position, sum, numbers, wheel) {
    if (position === numbers.length || sum === null) {
        return null;
    }
    wheel[position]++;
    if (wheel[position] === 2) {
        wheel[position] = 0;
        sum -= numbers[position];
        if (wheel.length < position + 2) {
            wheel.push(0);
        }
        sum = incrementWheel(position + 1, sum, numbers, wheel);
    }
    else {
        sum += numbers[position];
    }
    return sum;
}

-----------------------------------------------------------------
Alternate, more efficient version using Gray Code binary counting
technique as suggested in comment
-----------------------------------------------------------------

const numbers = [-0.47, -0.35, -0.19, 0.23, 0.36, 0.47, 0.51, 
    0.59, 0.63, 0.79, 0.85, 0.91, 0.99, 1.02, 1.17, 1.25,
     1.39, 1.44, 1.59, 1.60, 1.79, 1.88, 1.99, 2.14, 2.31];
const target = 24.16;

displaySubsetsThatSumTo(target, numbers);

function displaySubsetsThatSumTo(target, numbers)
{
    let resultsCount = 0;
    let sum = 0;
    let wheel = []; //binary counter
    let changeEvery = []; //how often each binary digit flips
    let nextChange = []; //when each binary digit will next flip
    for(let i = 0; i < numbers.length; i++) {
        //Initialize wheel and wheel-update data. Using Gray Code binary counting technique,
        //    whereby only one binary digit in the wheel changes on each iteration. Then only
        //    a single sum operation is required each iteration.
        wheel.push(0);
        changeEvery.push(2 ** (numbers.length - i));
        nextChange.push(2 ** (numbers.length - i - 1));
    }
   
    const start = new Date();

    const numIterations = 2 ** numbers.length;
    for (counter = 1; counter < numIterations; counter++) {
        for (let i = nextChange.length - 1; i >= 0; i--) {
            if(nextChange[i] === counter) {
                nextChange[i] += changeEvery[i];
                if (wheel[i] === 1) {
                    wheel[i] = 0;
                    sum -= numbers[i];
                }
                else {
                    wheel[i] = 1;
                    sum += numbers[i];
                }
                
                break;
            }
        }

        //Use subtraction comparison due to javascript float imprecision
        if (Math.abs(target - sum) < 0.000001) {
            //Found a subset. Display the result.
            console.log(numbers.filter((num, index) => wheel[index] === 1)
                .join(' + ') + ' = ' + target);
            resultsCount++;
        }
    }

    const end = new Date();
    
    console.log('--------------------------');
    console.log(`Processed ${numbers.length} numbers in ${(end - start) / 1000} seconds (${resultsCount} results)`);
}

C#

    public class Program
    {
        static void Main(string[] args)
        {
            double[] numbers = { -0.47, -0.35, -0.19, 0.23, 0.36, 0.47, 0.51, 0.59, 0.63, 0.79, 0.85,
                0.91, 0.99, 1.02, 1.17, 1.25, 1.39, 1.44, 1.59, 1.60, 1.79, 1.88, 1.99, 2.14, 2.31 };

            double target = 24.16;

            DisplaySubsetsThatSumTo(target, numbers);
        }

        private static void DisplaySubsetsThatSumTo(double Target, double[] numbers)
        {
            var stopwatch = new System.Diagnostics.Stopwatch();

            bool[] wheel = new bool[numbers.Length];
            int resultsCount = 0;
            double? sum = 0;

            stopwatch.Start();

            do
            {
                sum = IncrementWheel(0, sum, numbers, wheel);
                //Use subtraction comparison due to double type imprecision
                if (sum.HasValue && Math.Abs(sum.Value - Target) < 0.000001F)
                {
                    //Found a subset. Display the result.
                    Console.WriteLine(string.Join(" + ", numbers.Where((n, idx) => wheel[idx])) + " = " + Target);
                    resultsCount++;
                }
            } while (sum != null);

            stopwatch.Stop();

            Console.WriteLine("--------------------------");
            Console.WriteLine($"Processed {numbers.Length} numbers in {stopwatch.ElapsedMilliseconds / 1000.0} seconds ({resultsCount} results). Press any key to exit.");
            Console.ReadKey();
        }

        private static double? IncrementWheel(int Position, double? Sum, double[] numbers, bool[] wheel)
        {
            if (Position == numbers.Length || !Sum.HasValue)
            {
                return null;
            }
            wheel[Position] = !wheel[Position];
            if (!wheel[Position])
            {
                Sum -= numbers[Position];
                Sum = IncrementWheel(Position + 1, Sum, numbers, wheel);
            }
            else
            {
                Sum += numbers[Position];
            }
            return Sum;
        }
    }

Output

-0.35 + 0.23 + 0.36 + 0.47 + 0.51 + 0.59 + 0.63 + 0.79 + 0.85 + 0.91 + 0.99 + 1.02 + 1.17 + 1.25 + 1.44 + 1.59 + 1.6 + 1.79 + 1.88 + 1.99 + 2.14 + 2.31 = 24.16
0.23 + 0.51 + 0.59 + 0.63 + 0.79 + 0.85 + 0.99 + 1.02 + 1.17 + 1.25 + 1.39 + 1.44 + 1.59 + 1.6 + 1.79 + 1.88 + 1.99 + 2.14 + 2.31 = 24.16
-0.47 + 0.23 + 0.47 + 0.51 + 0.59 + 0.63 + 0.79 + 0.85 + 0.99 + 1.02 + 1.17 + 1.25 + 1.39 + 1.44 + 1.59 + 1.6 + 1.79 + 1.88 + 1.99 + 2.14 + 2.31 = 24.16
-0.19 + 0.36 + 0.51 + 0.59 + 0.63 + 0.79 + 0.91 + 0.99 + 1.02 + 1.17 + 1.25 + 1.39 + 1.44 + 1.59 + 1.6 + 1.79 + 1.88 + 1.99 + 2.14 + 2.31 = 24.16
-0.47 + -0.19 + 0.36 + 0.47 + 0.51 + 0.59 + 0.63 + 0.79 + 0.91 + 0.99 + 1.02 + 1.17 + 1.25 + 1.39 + 1.44 + 1.59 + 1.6 + 1.79 + 1.88 + 1.99 + 2.14 + 2.31 = 24.16
0.23 + 0.47 + 0.51 + 0.63 + 0.85 + 0.91 + 0.99 + 1.02 + 1.17 + 1.25 + 1.39 + 1.44 + 1.59 + 1.6 + 1.79 + 1.88 + 1.99 + 2.14 + 2.31 = 24.16
--------------------------
Processed 25 numbers in 0.823 seconds (6 results)

Following solution also provide array of subset which provide specific sum (here sum = 9)

array = [1, 3, 4, 2, 7, 8, 9]

(0..array.size).map { |i| array.combination(i).to_a.select { |a| a.sum == 9 } }.flatten(1)

return array of subsets which return sum of 9

 => [[9], [1, 8], [2, 7], [3, 4, 2]] 

I have solved this by java. This solution is quite simple.

import java.util.*;

public class Recursion {

static void sum(int[] arr, int i, int sum, int target, String s)
{   
    for(int j = i+1; j<arr.length; j++){
        if(sum+arr[j] == target){
            System.out.println(s+" "+String.valueOf(arr[j]));
        }else{
            sum(arr, j, sum+arr[j], target, s+" "+String.valueOf(arr[j]));
        }
    }
}

public static void main(String[] args)
{   
    int[] numbers = {6,3,8,10,1};
    for(int i =0; i<numbers.length; i++){
        sum(numbers, i, numbers[i], 18, String.valueOf(numbers[i])); 
    }

}
}

While it is straightforward to find if their is a subset or not that sums to the target, implementation gets tricky when you need to keep track of the partial subsets under consideration.

If you use a linked list, a hash set or any another generic collection, you would be tempted to add an item to this collection before the call that includes the item, and then remove it before the call that excludes the item. This does not work as expected, as the stack frames in which the add will occur is not the same as the one in which remove will occur.

Solution is to use a string to keep track of the sequence. Appends to the string can be done inline in the function call; thereby maintaining the same stack frame and your answer would then conform beautifully to the original hasSubSetSum recursive structure.

import java.util.ArrayList;

public class Solution {

public static boolean hasSubSet(int [] A, int target) {
    ArrayList<String> subsets = new ArrayList<>();
    helper(A, target, 0, 0, subsets, "");
    // Printing the contents of subsets is straightforward
    return !subsets.isEmpty();
}

private static void helper(int[] A, int target, int sumSoFar, int i, ArrayList<String> subsets, String curr) {
    if(i == A.length) {
        if(sumSoFar == target) {
            subsets.add(curr);
        }
        return;
    }
    helper(A, target, sumSoFar, i+1, subsets, curr);
    helper(A, target, sumSoFar + A[i], i+1, subsets, curr + A[i]);
}

public static void main(String [] args) {
    System.out.println(hasSubSet(new int[] {1,2,4,5,6}, 8));
}

}


I used Dynamic Programming & Memoization to find count of subsets from a set having a particular total. The code below code is in java. Have included the comments to explain the code intentions -

package com.company.dynamicProgramming;

import java.util.HashMap;
import java.util.Map;
import java.util.Objects;

public class FindSumInSubSet {

    public static void main(String...args){

        int[] arr = {3, 2, 4, 6, 10};
        int total = 16;
        // Challenge is to find the subsets of numbers total 6 in above super set (represented as array)
        // In general - Write a code to count subset of elements totalling m(6 above) in given set of n(9 as array size above) elements

        Map<Entry, Integer> memoMap = new HashMap<>();

        Entry entry = new Entry(total, arr.length-1);

        int count = countSubSetForSum(arr, entry, memoMap);
        System.out.format("In set of %d elements, the number of subsets having total=%d is %d %n", arr.length,total, count);
    }


    static int countSubSetForSum(int[] arr, Entry entry, Map<Entry, Integer> memoMap){

        int total = entry.getTotal();
        int i = entry.getI();

        if (total == 0){             // means element was equal in previous recursion
            return 1;
        }else if(total < 0){         // means element was less in previous recursion i.e. not equal
            return 0;
        }else if (i < 0){            // means arr was finished previous recursion
            return 0;
        }else if (arr[i] > total){   // means element is greater than total
                                     // i.e. leave that element and look further sets excluding this element
            return getCountForIthAndTotal(arr, new Entry( total, i-1), memoMap);

        }else{                       // means element is less than total i.e. 2 possibilities :
                                     // 1st - look further sets including this element
                                     // 2nd - look further sets excluding this element
            return getCountForIthAndTotal(arr, new Entry( total-arr[i], i-1), memoMap) +
                    getCountForIthAndTotal(arr, new Entry( total, i-1), memoMap);
        }
    }


    static int getCountForIthAndTotal(int[] arr, Entry entry, Map<Entry, Integer> memoMap){
        if (memoMap.containsKey(entry)){     //look up in has table if we already calculated particular total for ith subset..
            return memoMap.get(entry);       //This is nothing but using memoization that reduce the entire below code i.e. further recursion -
        }else {
            int count = countSubSetForSum(arr, entry, memoMap);  //Recursion
            memoMap.put(entry, count); //Build memoization
            return count;
        }
    }


    //Just Data Structure for Key in HashMap (memoMaP)... intent to include particular total for ith element's subset.
    static class Entry {
        int total;
        int i;

        public Entry(int total, int i) {
            this.total = total;
            this.i = i;
        }

        public int getTotal() {
            return total;
        }

        public int getI() {
            return i;
        }


        @Override
        public boolean equals(Object o) {
            if (this == o) return true;
            if (o == null || getClass() != o.getClass()) return false;
            Entry entry = (Entry) o;
            return total == entry.total &&
                    i == entry.i;
        }

        @Override
        public int hashCode() {
            return Objects.hash(total, i);
        }
    }

}

When i ran this the out put is :

In set of 5 elements, the number of subsets having total=16 is 2 
Process finished with exit code 0

Examples related to algorithm

How can I tell if an algorithm is efficient? Find the smallest positive integer that does not occur in a given sequence Efficiently getting all divisors of a given number Peak signal detection in realtime timeseries data What is the optimal algorithm for the game 2048? How can I sort a std::map first by value, then by key? Finding square root without using sqrt function? Fastest way to flatten / un-flatten nested JSON objects Mergesort with Python Find common substring between two strings

Examples related to recursion

List all the files and folders in a Directory with PHP recursive function Jquery Ajax beforeSend and success,error & complete Node.js - Maximum call stack size exceeded best way to get folder and file list in Javascript Recursive sub folder search and return files in a list python find all subsets that sum to a particular value jQuery - Uncaught RangeError: Maximum call stack size exceeded Find and Replace string in all files recursive using grep and sed recursion versus iteration Method to get all files within folder and subfolders that will return a list

Examples related to subset

how to remove multiple columns in r dataframe? Using grep to help subset a data frame in R Subset a dataframe by multiple factor levels creating a new list with subset of list using index in python subsetting a Python DataFrame Undefined columns selected when subsetting data frame How to select some rows with specific rownames from a dataframe? Subset data to contain only columns whose names match a condition find all subsets that sum to a particular value Subset and ggplot2