[JAVA] DFS pruning and de-duplication 1049. Last Stone Weight II

The underlying math problem is to split the array to two parts which have closest sum.
The most naive way is a depth first search.
However, a simple depth first search will cause TLE.
To speed up, the following is done.

  1. Sort array ( this enables de-duplication)
  2. de-duplication ( this can help on pruning for a lot of cases)
  3. pruning.
    With the above proper pruning applied,
    for the case of [1, 1, 1, 1, 1, 1], the dfs will traverse ONLY ONE branch 1, 1, 1, then it will return.
    Without pruning, the DFS will search for 2 ^ 6 branches.
class Solution {
    public int lastStoneWeightII(int[] stones) {
        if (stones.length == 1) return stones[0];
        int sum = 0;
        for (int n : stones) sum += n;
        Arrays.sort(stones); // sort array for de-duplication and  for pruning 
        int[] closest = new int[1];
        findClosestFloor(stones, 0, closest, sum / 2, 0);
        return sum - 2 * closest[0];
    }
    private void findClosestFloor(int[] stones, int index, int[] closest, int target, int cur) {
        
        if (closest[0] == target) return; // pruning
        if (cur > target) return; // pruning
        if (cur > closest[0] && cur <= target)  closest[0] = cur;//update result

        for (int i = index; i < stones.length; i++) {
            if (i != index && stones[i] == stones[i - 1]) continue; // de duplication
            findClosestFloor(stones, i + 1, closest, target, cur + stones[i]); // recursion
        }
    }
}

你可能感兴趣的:([JAVA] DFS pruning and de-duplication 1049. Last Stone Weight II)